diff options
Diffstat (limited to 'WebKit/mac/Misc')
76 files changed, 8167 insertions, 0 deletions
diff --git a/WebKit/mac/Misc/EmptyProtocolDefinitions.h b/WebKit/mac/Misc/EmptyProtocolDefinitions.h new file mode 100644 index 0000000..c52d8ce --- /dev/null +++ b/WebKit/mac/Misc/EmptyProtocolDefinitions.h @@ -0,0 +1,48 @@ +/* + * Copyright (C) 2008 Apple Inc. All Rights Reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#if defined(__OBJC__) + +#if defined(BUILDING_ON_TIGER) || defined(BUILDING_ON_LEOPARD) +#define DELEGATES_DECLARED_AS_FORMAL_PROTOCOLS 0 +#else +#define DELEGATES_DECLARED_AS_FORMAL_PROTOCOLS 1 +#endif + +#if !DELEGATES_DECLARED_AS_FORMAL_PROTOCOLS + +#define EMPTY_PROTOCOL(NAME) \ +@protocol NAME <NSObject> \ +@end + +EMPTY_PROTOCOL(NSTableViewDataSource) +EMPTY_PROTOCOL(NSTableViewDelegate) +EMPTY_PROTOCOL(NSWindowDelegate) + +#undef EMPTY_PROTOCOL + +#endif /* !DELEGATES_DECLARED_AS_FORMAL_PROTOCOLS */ + +#endif /* defined(__OBJC__) */ diff --git a/WebKit/mac/Misc/OldWebAssertions.c b/WebKit/mac/Misc/OldWebAssertions.c new file mode 100644 index 0000000..b84cdbc --- /dev/null +++ b/WebKit/mac/Misc/OldWebAssertions.c @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/* These functions are not used anymore, but need to stay for binary compatibility <rdar://problem/4841432>. */ +/* You should use <wtf/Assertions.h>. */ + +void WebReportAssertionFailure(const char *file, int line, const char *function, const char *assertion); +void WebReportError(const char *file, int line, const char *function, const char *format, ...); + +void WebReportAssertionFailure(const char *file, int line, const char *function, const char *assertion) +{ +} + +void WebReportError(const char *file, int line, const char *function, const char *format, ...) +{ +} diff --git a/WebKit/mac/Misc/WebAssertions.h b/WebKit/mac/Misc/WebAssertions.h new file mode 100644 index 0000000..4824090 --- /dev/null +++ b/WebKit/mac/Misc/WebAssertions.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/* This header is needed only for backwards-compatibility with internal clients + * which have yet to move away from it: <rdar://problem/5141290>. + */ + +#warning <WebKit/WebAssertions.h> is deprecated. Please move away from this SPI as soon as is possible. + +#define ASSERT(...) ((void)0) +#define ASSERT_NOT_REACHED(...) ((void)0) +#define ASSERT_ARG(...) ((void)0) +#define ERROR(...) ((void)0) diff --git a/WebKit/mac/Misc/WebCache.h b/WebKit/mac/Misc/WebCache.h new file mode 100644 index 0000000..1b5662b --- /dev/null +++ b/WebKit/mac/Misc/WebCache.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +@interface WebCache : NSObject +{ +} + ++ (NSArray *)statistics; ++ (void)empty; ++ (void)setDisabled:(BOOL)disabled; ++ (BOOL)isDisabled; + +@end diff --git a/WebKit/mac/Misc/WebCache.mm b/WebKit/mac/Misc/WebCache.mm new file mode 100644 index 0000000..d3dfbdb --- /dev/null +++ b/WebKit/mac/Misc/WebCache.mm @@ -0,0 +1,105 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebCache.h" + +#import "WebPreferences.h" +#import "WebView.h" +#import "WebViewInternal.h" +#import <WebCore/ApplicationCacheStorage.h> +#import <WebCore/Cache.h> + +@implementation WebCache + ++ (NSArray *)statistics +{ + WebCore::Cache::Statistics s = WebCore::cache()->getStatistics(); + + return [NSArray arrayWithObjects: + [NSDictionary dictionaryWithObjectsAndKeys: + [NSNumber numberWithInt:s.images.count], @"Images", + [NSNumber numberWithInt:s.cssStyleSheets.count], @"CSS", +#if ENABLE(XSLT) + [NSNumber numberWithInt:s.xslStyleSheets.count], @"XSL", +#else + [NSNumber numberWithInt:0], @"XSL", +#endif + [NSNumber numberWithInt:s.scripts.count], @"JavaScript", + nil], + [NSDictionary dictionaryWithObjectsAndKeys: + [NSNumber numberWithInt:s.images.size], @"Images", + [NSNumber numberWithInt:s.cssStyleSheets.size] ,@"CSS", +#if ENABLE(XSLT) + [NSNumber numberWithInt:s.xslStyleSheets.size], @"XSL", +#else + [NSNumber numberWithInt:0], @"XSL", +#endif + [NSNumber numberWithInt:s.scripts.size], @"JavaScript", + nil], + [NSDictionary dictionaryWithObjectsAndKeys: + [NSNumber numberWithInt:s.images.liveSize], @"Images", + [NSNumber numberWithInt:s.cssStyleSheets.liveSize] ,@"CSS", +#if ENABLE(XSLT) + [NSNumber numberWithInt:s.xslStyleSheets.liveSize], @"XSL", +#else + [NSNumber numberWithInt:0], @"XSL", +#endif + [NSNumber numberWithInt:s.scripts.liveSize], @"JavaScript", + nil], + [NSDictionary dictionaryWithObjectsAndKeys: + [NSNumber numberWithInt:s.images.decodedSize], @"Images", + [NSNumber numberWithInt:s.cssStyleSheets.decodedSize] ,@"CSS", +#if ENABLE(XSLT) + [NSNumber numberWithInt:s.xslStyleSheets.decodedSize], @"XSL", +#else + [NSNumber numberWithInt:0], @"XSL", +#endif + [NSNumber numberWithInt:s.scripts.decodedSize], @"JavaScript", + nil], + nil]; +} + ++ (void)empty +{ + // Toggling the cache model like this forces the cache to evict all its in-memory resources. + WebCacheModel cacheModel = [WebView _cacheModel]; + [WebView _setCacheModel:WebCacheModelDocumentViewer]; + [WebView _setCacheModel:cacheModel]; + + // Empty the application cache. + WebCore::cacheStorage().empty(); +} + ++ (void)setDisabled:(BOOL)disabled +{ + WebCore::cache()->setDisabled(disabled); +} + ++ (BOOL)isDisabled +{ + return WebCore::cache()->disabled(); +} + +@end diff --git a/WebKit/mac/Misc/WebCoreStatistics.h b/WebKit/mac/Misc/WebCoreStatistics.h new file mode 100644 index 0000000..392f31b --- /dev/null +++ b/WebKit/mac/Misc/WebCoreStatistics.h @@ -0,0 +1,77 @@ +/* + * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +#import <WebKit/WebFrame.h> + +@interface WebCoreStatistics : NSObject +{ +} + ++ (NSArray *)statistics; + ++ (size_t)javaScriptObjectsCount; ++ (size_t)javaScriptGlobalObjectsCount; ++ (size_t)javaScriptProtectedObjectsCount; ++ (size_t)javaScriptProtectedGlobalObjectsCount; ++ (NSCountedSet *)javaScriptProtectedObjectTypeCounts; + ++ (void)garbageCollectJavaScriptObjects; ++ (void)garbageCollectJavaScriptObjectsOnAlternateThreadForDebugging:(BOOL)waitUntilDone; + ++ (size_t)iconPageURLMappingCount; ++ (size_t)iconRetainedPageURLCount; ++ (size_t)iconRecordCount; ++ (size_t)iconsWithDataCount; + ++ (size_t)cachedFontDataCount; ++ (size_t)cachedFontDataInactiveCount; ++ (void)purgeInactiveFontData; ++ (size_t)glyphPageCount; + ++ (BOOL)shouldPrintExceptions; ++ (void)setShouldPrintExceptions:(BOOL)print; + ++ (void)startIgnoringWebCoreNodeLeaks; ++ (void)stopIgnoringWebCoreNodeLeaks; + +// Deprecated, but used by older versions of Safari. ++ (void)emptyCache; ++ (void)setCacheDisabled:(BOOL)disabled; ++ (size_t)javaScriptNoGCAllowedObjectsCount; ++ (size_t)javaScriptReferencedObjectsCount; ++ (NSSet *)javaScriptRootObjectClasses; ++ (NSCountedSet *)javaScriptRootObjectTypeCounts; ++ (size_t)javaScriptInterpretersCount; + +@end + +@interface WebFrame (WebKitDebug) +- (NSString *)renderTreeAsExternalRepresentation; +@end diff --git a/WebKit/mac/Misc/WebCoreStatistics.mm b/WebKit/mac/Misc/WebCoreStatistics.mm new file mode 100644 index 0000000..ecbfe9d --- /dev/null +++ b/WebKit/mac/Misc/WebCoreStatistics.mm @@ -0,0 +1,211 @@ +/* + * Copyright (C) 2005, 2006, 2008 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebCoreStatistics.h" + +#import "WebCache.h" +#import "WebFrameInternal.h" +#import <runtime/JSLock.h> +#import <WebCore/Console.h> +#import <WebCore/FontCache.h> +#import <WebCore/Frame.h> +#import <WebCore/GCController.h> +#import <WebCore/GlyphPageTreeNode.h> +#import <WebCore/IconDatabase.h> +#import <WebCore/JSDOMWindow.h> +#import <WebCore/RenderTreeAsText.h> +#import <WebCore/RenderView.h> + +using namespace JSC; +using namespace WebCore; + +@implementation WebCoreStatistics + ++ (NSArray *)statistics +{ + return [WebCache statistics]; +} + ++ (size_t)javaScriptObjectsCount +{ + JSLock lock(false); + return JSDOMWindow::commonJSGlobalData()->heap.size(); +} + ++ (size_t)javaScriptGlobalObjectsCount +{ + JSLock lock(false); + return JSDOMWindow::commonJSGlobalData()->heap.globalObjectCount(); +} + ++ (size_t)javaScriptProtectedObjectsCount +{ + JSLock lock(false); + return JSDOMWindow::commonJSGlobalData()->heap.protectedObjectCount(); +} + ++ (size_t)javaScriptProtectedGlobalObjectsCount +{ + JSLock lock(false); + return JSDOMWindow::commonJSGlobalData()->heap.protectedGlobalObjectCount(); +} + ++ (NSCountedSet *)javaScriptProtectedObjectTypeCounts +{ + JSLock lock(false); + + NSCountedSet *result = [NSCountedSet set]; + + OwnPtr<HashCountedSet<const char*> > counts(JSDOMWindow::commonJSGlobalData()->heap.protectedObjectTypeCounts()); + HashCountedSet<const char*>::iterator end = counts->end(); + for (HashCountedSet<const char*>::iterator it = counts->begin(); it != end; ++it) + for (unsigned i = 0; i < it->second; ++i) + [result addObject:[NSString stringWithUTF8String:it->first]]; + + return result; +} + ++ (void)garbageCollectJavaScriptObjects +{ + gcController().garbageCollectNow(); +} + ++ (void)garbageCollectJavaScriptObjectsOnAlternateThreadForDebugging:(BOOL)waitUntilDone; +{ + gcController().garbageCollectOnAlternateThreadForDebugging(waitUntilDone); +} + ++ (size_t)iconPageURLMappingCount +{ + return iconDatabase()->pageURLMappingCount(); +} + ++ (size_t)iconRetainedPageURLCount +{ + return iconDatabase()->retainedPageURLCount(); +} + ++ (size_t)iconRecordCount +{ + return iconDatabase()->iconRecordCount(); +} + ++ (size_t)iconsWithDataCount +{ + return iconDatabase()->iconRecordCountWithData(); +} + ++ (size_t)cachedFontDataCount +{ + return FontCache::fontDataCount(); +} + ++ (size_t)cachedFontDataInactiveCount +{ + return FontCache::inactiveFontDataCount(); +} + ++ (void)purgeInactiveFontData +{ + FontCache::purgeInactiveFontData(); +} + ++ (size_t)glyphPageCount +{ + return GlyphPageTreeNode::treeGlyphPageCount(); +} + ++ (BOOL)shouldPrintExceptions +{ + JSLock lock(false); + return Console::shouldPrintExceptions(); +} + ++ (void)setShouldPrintExceptions:(BOOL)print +{ + JSLock lock(false); + Console::setShouldPrintExceptions(print); +} + ++ (void)emptyCache +{ + [WebCache empty]; +} + ++ (void)setCacheDisabled:(BOOL)disabled +{ + [WebCache setDisabled:disabled]; +} + ++ (void)startIgnoringWebCoreNodeLeaks +{ + WebCore::Node::startIgnoringLeaks(); +} + ++ (void)stopIgnoringWebCoreNodeLeaks; +{ + WebCore::Node::stopIgnoringLeaks(); +} + +// Deprecated ++ (size_t)javaScriptNoGCAllowedObjectsCount +{ + return 0; +} + ++ (size_t)javaScriptReferencedObjectsCount +{ + JSLock lock(false); + return JSDOMWindow::commonJSGlobalData()->heap.protectedObjectCount(); +} + ++ (NSSet *)javaScriptRootObjectClasses +{ + return [self javaScriptRootObjectTypeCounts]; +} + ++ (size_t)javaScriptInterpretersCount +{ + return [self javaScriptProtectedGlobalObjectsCount]; +} + ++ (NSCountedSet *)javaScriptRootObjectTypeCounts +{ + return [self javaScriptProtectedObjectTypeCounts]; +} + +@end + +@implementation WebFrame (WebKitDebug) + +- (NSString *)renderTreeAsExternalRepresentation +{ + return externalRepresentation(_private->coreFrame->contentRenderer()); +} + +@end diff --git a/WebKit/mac/Misc/WebDownload.h b/WebKit/mac/Misc/WebDownload.h new file mode 100644 index 0000000..68dfda9 --- /dev/null +++ b/WebKit/mac/Misc/WebDownload.h @@ -0,0 +1,67 @@ +/* + * Copyright (C) 2003 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/NSURLDownload.h> + +@class WebDownloadInternal; + +/*! + @class WebDownload + @discussion A WebDownload works just like an NSURLDownload, with + one extra feature: if you do not implement the + authentication-related delegate methods, it will automatically + prompt for authentication using the standard WebKit authentication + panel, as either a sheet or window. It provides no extra methods, + but does have one additional delegate method. +*/ + + +@interface WebDownload : NSURLDownload +{ +@private + WebDownloadInternal *_webInternal; +} + +@end + +/*! + @protocol WebDownloadDelegate + @discussion The WebDownloadDelegate delegate has one extra method used to choose + the right window when automatically prompting with a sheet. +*/ +@interface NSObject (WebDownloadDelegate) + +/*! + @method downloadWindowForAuthenticationSheet: + @abstract + @param + @result +*/ +- (NSWindow *)downloadWindowForAuthenticationSheet:(WebDownload *)download; + +@end diff --git a/WebKit/mac/Misc/WebDownload.m b/WebKit/mac/Misc/WebDownload.m new file mode 100644 index 0000000..2c53c1b --- /dev/null +++ b/WebKit/mac/Misc/WebDownload.m @@ -0,0 +1,249 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebDownload.h> + +#import <Foundation/NSURLAuthenticationChallenge.h> +#import <Foundation/NSURLDownload.h> +#import <WebKit/WebPanelAuthenticationHandler.h> +#import <wtf/Assertions.h> + +#import "WebTypesInternal.h" + +@class NSURLConnectionDelegateProxy; + +// FIXME: The following are NSURLDownload SPI - it would be nice to not have to override them at +// some point in the future +@interface NSURLDownload (WebDownloadCapability) +- (id)_initWithLoadingConnection:(NSURLConnection *)connection + request:(NSURLRequest *)request + response:(NSURLResponse *)response + delegate:(id)delegate + proxy:(NSURLConnectionDelegateProxy *)proxy; +- (id)_initWithRequest:(NSURLRequest *)request + delegate:(id)delegate + directory:(NSString *)directory; +@end + +@interface WebDownloadInternal : NSObject +{ +@public + id realDelegate; +} + +- (void)setRealDelegate:(id)rd; + +@end + +@implementation WebDownloadInternal + +- (void)dealloc +{ + [realDelegate release]; + [super dealloc]; +} + +- (void)setRealDelegate:(id)rd +{ + [rd retain]; + [realDelegate release]; + realDelegate = rd; +} + +- (BOOL)respondsToSelector:(SEL)selector +{ + if (selector == @selector(downloadDidBegin:) || + selector == @selector(download:willSendRequest:redirectResponse:) || + selector == @selector(download:didReceiveResponse:) || + selector == @selector(download:didReceiveDataOfLength:) || + selector == @selector(download:shouldDecodeSourceDataOfMIMEType:) || + selector == @selector(download:decideDestinationWithSuggestedFilename:) || + selector == @selector(download:didCreateDestination:) || + selector == @selector(downloadDidFinish:) || + selector == @selector(download:didFailWithError:) || + selector == @selector(download:shouldBeginChildDownloadOfSource:delegate:) || + selector == @selector(download:didBeginChildDownload:)) { + return [realDelegate respondsToSelector:selector]; + } + + return [super respondsToSelector:selector]; +} + +- (void)downloadDidBegin:(NSURLDownload *)download +{ +#if !defined(BUILDING_ON_TIGER) && !defined(BUILDING_ON_LEOPARD) + [[NSProcessInfo processInfo] disableSuddenTermination]; +#endif + [realDelegate downloadDidBegin:download]; +} + +- (NSURLRequest *)download:(NSURLDownload *)download willSendRequest:(NSURLRequest *)request redirectResponse:(NSURLResponse *)redirectResponse +{ + return [realDelegate download:download willSendRequest:request redirectResponse:redirectResponse]; +} + +- (void)download:(NSURLDownload *)download didReceiveAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge +{ + if ([realDelegate respondsToSelector:@selector(download:didReceiveAuthenticationChallenge:)]) { + [realDelegate download:download didReceiveAuthenticationChallenge:challenge]; + } else { + NSWindow *window = nil; + if ([realDelegate respondsToSelector:@selector(downloadWindowForAuthenticationSheet:)]) { + window = [realDelegate downloadWindowForAuthenticationSheet:(WebDownload *)download]; + } + + [[WebPanelAuthenticationHandler sharedHandler] startAuthentication:challenge window:window]; + } +} + +- (void)download:(NSURLDownload *)download didCancelAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge +{ + if ([realDelegate respondsToSelector:@selector(download:didCancelAuthenticationChallenge:)]) { + [realDelegate download:download didCancelAuthenticationChallenge:challenge]; + } else { + [[WebPanelAuthenticationHandler sharedHandler] cancelAuthentication:challenge]; + } +} + +- (void)download:(NSURLDownload *)download didReceiveResponse:(NSURLResponse *)response +{ + [realDelegate download:download didReceiveResponse:response]; +} + +- (void)download:(NSURLDownload *)download didReceiveDataOfLength:(NSUInteger)length +{ + [realDelegate download:download didReceiveDataOfLength:length]; +} + +- (BOOL)download:(NSURLDownload *)download shouldDecodeSourceDataOfMIMEType:(NSString *)encodingType +{ + return [realDelegate download:download shouldDecodeSourceDataOfMIMEType:encodingType]; +} + +- (void)download:(NSURLDownload *)download decideDestinationWithSuggestedFilename:(NSString *)filename +{ + [realDelegate download:download decideDestinationWithSuggestedFilename:filename]; +} + +- (void)download:(NSURLDownload *)download didCreateDestination:(NSString *)path +{ + [realDelegate download:download didCreateDestination:path]; +} + +- (void)downloadDidFinish:(NSURLDownload *)download +{ +#if !defined(BUILDING_ON_TIGER) && !defined(BUILDING_ON_LEOPARD) + [[NSProcessInfo processInfo] enableSuddenTermination]; +#endif + [realDelegate downloadDidFinish:download]; +} + +- (void)download:(NSURLDownload *)download didFailWithError:(NSError *)error +{ +#if !defined(BUILDING_ON_TIGER) && !defined(BUILDING_ON_LEOPARD) + [[NSProcessInfo processInfo] enableSuddenTermination]; +#endif + [realDelegate download:download didFailWithError:error]; +} + +- (NSURLRequest *)download:(NSURLDownload *)download shouldBeginChildDownloadOfSource:(NSURLRequest *)child delegate:(id *)childDelegate +{ + return [realDelegate download:download shouldBeginChildDownloadOfSource:child delegate:childDelegate]; +} + +- (void)download:(NSURLDownload *)parent didBeginChildDownload:(NSURLDownload *)child +{ + [realDelegate download:parent didBeginChildDownload:child]; +} + +@end + +@implementation WebDownload + +- (void)_setRealDelegate:(id)delegate +{ + if (_webInternal == nil) { + _webInternal = [[WebDownloadInternal alloc] init]; + [_webInternal setRealDelegate:delegate]; + } else { + ASSERT(_webInternal == delegate); + } +} + +- (id)init +{ + self = [super init]; + if (self != nil) { + // _webInternal can be set up before init by _setRealDelegate + if (_webInternal == nil) { + _webInternal = [[WebDownloadInternal alloc] init]; + } + } + return self; +} + +- (void)dealloc +{ + [_webInternal release]; + [super dealloc]; +} + +- (id)initWithRequest:(NSURLRequest *)request delegate:(id)delegate +{ + [self _setRealDelegate:delegate]; + return [super initWithRequest:request delegate:_webInternal]; +} + +- (id)_initWithLoadingConnection:(NSURLConnection *)connection + request:(NSURLRequest *)request + response:(NSURLResponse *)response + delegate:(id)delegate + proxy:(NSURLConnectionDelegateProxy *)proxy +{ + [self _setRealDelegate:delegate]; + return [super _initWithLoadingConnection:connection request:request response:response delegate:_webInternal proxy:proxy]; +} + +- (id)_initWithRequest:(NSURLRequest *)request + delegate:(id)delegate + directory:(NSString *)directory +{ + [self _setRealDelegate:delegate]; + return [super _initWithRequest:request delegate:_webInternal directory:directory]; +} + +- (void)connection:(NSURLConnection *)connection willStopBufferingData:(NSData *)data +{ + // NSURLConnection calls this method even if it is not implemented. + // This happens because NSURLConnection caches the results of respondsToSelector. + // Those results become invalid when the delegate of NSURLConnectionDelegateProxy is changed. + // This is a workaround since this problem needs to be fixed in NSURLConnectionDelegateProxy. + // <rdar://problem/3913270> NSURLConnection calls unimplemented delegate method in WebDownload +} + +@end diff --git a/WebKit/mac/Misc/WebDownloadInternal.h b/WebKit/mac/Misc/WebDownloadInternal.h new file mode 100644 index 0000000..aaed445 --- /dev/null +++ b/WebKit/mac/Misc/WebDownloadInternal.h @@ -0,0 +1,41 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +#import <WebKit/WebDownload.h> + +@interface WebDownload (WebDownloadCreation) ++(id)_downloadWithLoadingConnection:(NSURLConnection *)connection + request:(NSURLRequest *)request + response:(NSURLResponse *)r + delegate:(id)delegate + proxy:(id)proxy; + ++(id)_downloadWithRequest:(NSURLRequest *)request + delegate:(id)delegate + directory:(NSString *)directory; +@end diff --git a/WebKit/mac/Misc/WebElementDictionary.h b/WebKit/mac/Misc/WebElementDictionary.h new file mode 100644 index 0000000..b835b5c --- /dev/null +++ b/WebKit/mac/Misc/WebElementDictionary.h @@ -0,0 +1,42 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/NSDictionary.h> + +namespace WebCore { + class HitTestResult; +} + +@interface WebElementDictionary : NSDictionary { + WebCore::HitTestResult* _result; + NSMutableDictionary *_cache; + NSMutableSet *_nilValues; + BOOL _cacheComplete; +} +- (id)initWithHitTestResult:(const WebCore::HitTestResult&)result; +@end diff --git a/WebKit/mac/Misc/WebElementDictionary.mm b/WebKit/mac/Misc/WebElementDictionary.mm new file mode 100644 index 0000000..b987525 --- /dev/null +++ b/WebKit/mac/Misc/WebElementDictionary.mm @@ -0,0 +1,252 @@ +/* + * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebElementDictionary.h" + +#import "WebDOMOperations.h" +#import "WebFrame.h" +#import "WebFrameInternal.h" +#import "WebKitLogging.h" +#import "WebTypesInternal.h" +#import "WebView.h" +#import "WebViewPrivate.h" +#import <WebCore/Frame.h> +#import <WebCore/HitTestResult.h> +#import <WebCore/Image.h> +#import <WebCore/WebCoreObjCExtras.h> +#import <WebKit/DOMCore.h> +#import <WebKit/DOMExtensions.h> + +using namespace WebCore; + +static CFMutableDictionaryRef lookupTable = NULL; + +static void addLookupKey(NSString *key, SEL selector) +{ + CFDictionaryAddValue(lookupTable, key, selector); +} + +static void cacheValueForKey(const void *key, const void *value, void *self) +{ + // calling objectForKey will cache the value in our _cache dictionary + [(WebElementDictionary *)self objectForKey:(NSString *)key]; +} + +@implementation WebElementDictionary + +#ifndef BUILDING_ON_TIGER ++ (void)initialize +{ + WebCoreObjCFinalizeOnMainThread(self); +} +#endif + ++ (void)initializeLookupTable +{ + if (lookupTable) + return; + + lookupTable = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFCopyStringDictionaryKeyCallBacks, NULL); + + addLookupKey(WebElementDOMNodeKey, @selector(_domNode)); + addLookupKey(WebElementFrameKey, @selector(_webFrame)); + addLookupKey(WebElementImageAltStringKey, @selector(_altDisplayString)); + addLookupKey(WebElementImageKey, @selector(_image)); + addLookupKey(WebElementImageRectKey, @selector(_imageRect)); + addLookupKey(WebElementImageURLKey, @selector(_absoluteImageURL)); + addLookupKey(WebElementIsSelectedKey, @selector(_isSelected)); + addLookupKey(WebElementSpellingToolTipKey, @selector(_spellingToolTip)); + addLookupKey(WebElementTitleKey, @selector(_title)); + addLookupKey(WebElementLinkURLKey, @selector(_absoluteLinkURL)); + addLookupKey(WebElementLinkTargetFrameKey, @selector(_targetWebFrame)); + addLookupKey(WebElementLinkTitleKey, @selector(_titleDisplayString)); + addLookupKey(WebElementLinkLabelKey, @selector(_textContent)); + addLookupKey(WebElementLinkIsLiveKey, @selector(_isLiveLink)); + addLookupKey(WebElementIsContentEditableKey, @selector(_isContentEditable)); +} + +- (id)initWithHitTestResult:(const HitTestResult&)result +{ + [[self class] initializeLookupTable]; + [super init]; + _result = new HitTestResult(result); + return self; +} + +- (void)dealloc +{ + if (WebCoreObjCScheduleDeallocateOnMainThread([WebElementDictionary class], self)) + return; + + delete _result; + [_cache release]; + [_nilValues release]; + [super dealloc]; +} + +- (void)finalize +{ + ASSERT_MAIN_THREAD(); + delete _result; + [super finalize]; +} + +- (void)_fillCache +{ + CFDictionaryApplyFunction(lookupTable, cacheValueForKey, self); + _cacheComplete = YES; +} + +- (NSUInteger)count +{ + if (!_cacheComplete) + [self _fillCache]; + return [_cache count]; +} + +- (NSEnumerator *)keyEnumerator +{ + if (!_cacheComplete) + [self _fillCache]; + return [_cache keyEnumerator]; +} + +- (id)objectForKey:(id)key +{ + id value = [_cache objectForKey:key]; + if (value || _cacheComplete || [_nilValues containsObject:key]) + return value; + + SEL selector = (SEL)CFDictionaryGetValue(lookupTable, key); + if (!selector) + return nil; + value = [self performSelector:selector]; + + unsigned lookupTableCount = CFDictionaryGetCount(lookupTable); + if (value) { + if (!_cache) + _cache = [[NSMutableDictionary alloc] initWithCapacity:lookupTableCount]; + [_cache setObject:value forKey:key]; + } else { + if (!_nilValues) + _nilValues = [[NSMutableSet alloc] initWithCapacity:lookupTableCount]; + [_nilValues addObject:key]; + } + + _cacheComplete = ([_cache count] + [_nilValues count]) == lookupTableCount; + + return value; +} + +- (DOMNode *)_domNode +{ + return kit(_result->innerNonSharedNode()); +} + +- (WebFrame *)_webFrame +{ + return [[[self _domNode] ownerDocument] webFrame]; +} + +// String's NSString* operator converts null Strings to empty NSStrings for compatibility +// with AppKit. We need to work around that here. +static NSString* NSStringOrNil(String coreString) +{ + if (coreString.isNull()) + return nil; + return coreString; +} + +- (NSString *)_altDisplayString +{ + return NSStringOrNil(_result->altDisplayString()); +} + +- (NSString *)_spellingToolTip +{ + return NSStringOrNil(_result->spellingToolTip()); +} + +- (NSImage *)_image +{ + Image* image = _result->image(); + return image ? image->getNSImage() : nil; +} + +- (NSValue *)_imageRect +{ + IntRect rect = _result->imageRect(); + return rect.isEmpty() ? nil : [NSValue valueWithRect:rect]; +} + +- (NSURL *)_absoluteImageURL +{ + return _result->absoluteImageURL(); +} + +- (NSNumber *)_isSelected +{ + return [NSNumber numberWithBool:_result->isSelected()]; +} + +- (NSString *)_title +{ + return NSStringOrNil(_result->title()); +} + +- (NSURL *)_absoluteLinkURL +{ + return _result->absoluteLinkURL(); +} + +- (WebFrame *)_targetWebFrame +{ + return kit(_result->targetFrame()); +} + +- (NSString *)_titleDisplayString +{ + return NSStringOrNil(_result->titleDisplayString()); +} + +- (NSString *)_textContent +{ + return NSStringOrNil(_result->textContent()); +} + +- (NSNumber *)_isLiveLink +{ + return [NSNumber numberWithBool:_result->isLiveLink()]; +} + +- (NSNumber *)_isContentEditable +{ + return [NSNumber numberWithBool:_result->isContentEditable()]; +} + +@end diff --git a/WebKit/mac/Misc/WebGraphicsExtras.c b/WebKit/mac/Misc/WebGraphicsExtras.c new file mode 100644 index 0000000..4d36b58 --- /dev/null +++ b/WebKit/mac/Misc/WebGraphicsExtras.c @@ -0,0 +1,57 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebGraphicsExtras.h" + +#import <Accelerate/Accelerate.h> +#import <dlfcn.h> +#import <wtf/Assertions.h> + +unsigned WebConvertBGRAToARGB(unsigned char *offscreenBuffer, int rowBytes, int x, int y, int width, int height) +{ + + static vImage_Error (*softLink_vImagePermuteChannels_ARGB8888)(const vImage_Buffer *src, const vImage_Buffer *dest, const uint8_t permuteMap[4], vImage_Flags flags) = NULL; + + if (!softLink_vImagePermuteChannels_ARGB8888) { + void *framework = dlopen("/System/Library/Frameworks/Accelerate.framework/Accelerate", RTLD_NOW); + ASSERT(framework); + softLink_vImagePermuteChannels_ARGB8888 = dlsym(framework, "vImagePermuteChannels_ARGB8888"); + ASSERT(softLink_vImagePermuteChannels_ARGB8888); + } + + void *swizzleImageBase = offscreenBuffer + y * rowBytes + x * 4; + vImage_Buffer vImage = { swizzleImageBase, height, width, rowBytes }; + uint8_t vImagePermuteMap[4] = { 3, 2, 1, 0 }; // Where { 0, 1, 2, 3 } would leave the channels unchanged; this map converts BGRA to ARGB + vImage_Error vImageError = softLink_vImagePermuteChannels_ARGB8888(&vImage, &vImage, vImagePermuteMap, 0); + if (vImageError) { + LOG_ERROR("Could not convert BGRA image to ARGB: %zd", vImageError); + return FALSE; + } + + return TRUE; +} diff --git a/WebKit/mac/Misc/WebGraphicsExtras.h b/WebKit/mac/Misc/WebGraphicsExtras.h new file mode 100644 index 0000000..9232303 --- /dev/null +++ b/WebKit/mac/Misc/WebGraphicsExtras.h @@ -0,0 +1,37 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifdef __cplusplus +extern "C" { +#endif + +unsigned WebConvertBGRAToARGB(unsigned char *offscreenBuffer, int rowBytes, int x, int y, int width, int height); + +#ifdef __cplusplus +} +#endif diff --git a/WebKit/mac/Misc/WebIconDatabase.h b/WebKit/mac/Misc/WebIconDatabase.h new file mode 100644 index 0000000..8dc3d45 --- /dev/null +++ b/WebKit/mac/Misc/WebIconDatabase.h @@ -0,0 +1,146 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + +// Sent whenever a site icon has changed. The object of the notification is the icon database. +// The userInfo contains the site URL whose icon has changed. +// It can be accessed with the key WebIconNotificationUserInfoURLKey. +extern NSString *WebIconDatabaseDidAddIconNotification; + +extern NSString *WebIconNotificationUserInfoURLKey; + +extern NSString *WebIconDatabaseDirectoryDefaultsKey; +extern NSString *WebIconDatabaseEnabledDefaultsKey; + +extern NSSize WebIconSmallSize; // 16 x 16 +extern NSSize WebIconMediumSize; // 32 x 32 +extern NSSize WebIconLargeSize; // 128 x 128 + +@class WebIconDatabasePrivate; + +/*! + @class WebIconDatabase + @discussion Features: + - memory cache icons at different sizes + - disk storage + - icon update notification + + Uses: + - UI elements to retrieve icons that represent site URLs. + - Save icons to disk for later use. + + Every icon in the database has a retain count. If an icon has a retain count greater than 0, it will be written to disk for later use. If an icon's retain count equals zero it will be removed from disk. The retain count is not persistent across launches. If the WebKit client wishes to retain an icon it should retain the icon once for every launch. This is best done at initialization time before the database begins removing icons. To make sure that the database does not remove unretained icons prematurely, call delayDatabaseCleanup until all desired icons are retained. Once all are retained, call allowDatabaseCleanup. + + Note that an icon can be retained after the database clean-up has begun. This just has to be done before the icon is removed. Icons are removed from the database whenever new icons are added to it. + + Retention methods can be called for icons that are not yet in the database. +*/ +@interface WebIconDatabase : NSObject { + +@private + WebIconDatabasePrivate *_private; + BOOL _isClosing; +} + + +/*! + @method sharedIconDatabase + @abstract Returns a shared instance of the icon database +*/ ++ (WebIconDatabase *)sharedIconDatabase; + +/*! + @method iconForURL:withSize: + @discussion Calls iconForURL:withSize:cache: with YES for cache. + @param URL + @param size +*/ +- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size; + +/*! + @method iconForURL:withSize:cache: + @discussion Returns an icon for a web site URL from memory or disk. nil if none is found. + Usually called by a UI element to determine if a site URL has an associated icon. + Often called by the observer of WebIconChangedNotification after the notification is sent. + @param URL + @param size + @param cache If yes, caches the returned image in memory if not already cached +*/ +- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size cache:(BOOL)cache; + +/*! + @method iconURLForURL:withSize:cache: + @discussion Returns an icon URL for a web site URL from memory or disk. nil if none is found. + @param URL +*/ +- (NSString *)iconURLForURL:(NSString *)URL; + +/*! + @method defaultIconWithSize: + @param size +*/ +- (NSImage *)defaultIconWithSize:(NSSize)size; +- (NSImage *)defaultIconForURL:(NSString *)URL withSize:(NSSize)size; + +/*! + @method retainIconForURL: + @abstract Increments the retain count of the icon. + @param URL +*/ +- (void)retainIconForURL:(NSString *)URL; + +/*! + @method releaseIconForURL: + @abstract Decrements the retain count of the icon. + @param URL +*/ +- (void)releaseIconForURL:(NSString *)URL; + +/*! + @method delayDatabaseCleanup: + @discussion Only effective if called before the database begins removing icons. + delayDatabaseCleanUp increments an internal counter that when 0 begins the database clean-up. + The counter equals 0 at initialization. +*/ ++ (void)delayDatabaseCleanup; + +/*! + @method allowDatabaseCleanup: + @discussion Informs the database that it now can begin removing icons. + allowDatabaseCleanup decrements an internal counter that when 0 begins the database clean-up. + The counter equals 0 at initialization. +*/ ++ (void)allowDatabaseCleanup; + +- (void)setDelegate:(id)delegate; +- (id)delegate; + +@end + + diff --git a/WebKit/mac/Misc/WebIconDatabase.mm b/WebKit/mac/Misc/WebIconDatabase.mm new file mode 100644 index 0000000..d911f0c --- /dev/null +++ b/WebKit/mac/Misc/WebIconDatabase.mm @@ -0,0 +1,670 @@ +/* + * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebIconDatabaseInternal.h" + +#import "WebIconDatabaseClient.h" +#import "WebIconDatabaseDelegate.h" +#import "WebKitLogging.h" +#import "WebKitNSStringExtras.h" +#import "WebNSFileManagerExtras.h" +#import "WebNSNotificationCenterExtras.h" +#import "WebNSURLExtras.h" +#import "WebPreferences.h" +#import "WebTypesInternal.h" +#import <WebCore/FoundationExtras.h> +#import <WebCore/IconDatabase.h> +#import <WebCore/Image.h> +#import <WebCore/IntSize.h> +#import <WebCore/ThreadCheck.h> + +using namespace WebCore; + +NSString * const WebIconDatabaseVersionKey = @"WebIconDatabaseVersion"; +NSString * const WebURLToIconURLKey = @"WebSiteURLToIconURLKey"; + +NSString *WebIconDatabaseDidAddIconNotification = @"WebIconDatabaseDidAddIconNotification"; +NSString *WebIconNotificationUserInfoURLKey = @"WebIconNotificationUserInfoURLKey"; +NSString *WebIconDatabaseDidRemoveAllIconsNotification = @"WebIconDatabaseDidRemoveAllIconsNotification"; + +NSString *WebIconDatabaseDirectoryDefaultsKey = @"WebIconDatabaseDirectoryDefaultsKey"; +NSString *WebIconDatabaseImportDirectoryDefaultsKey = @"WebIconDatabaseImportDirectoryDefaultsKey"; +NSString *WebIconDatabaseEnabledDefaultsKey = @"WebIconDatabaseEnabled"; + +NSString *WebIconDatabasePath = @"~/Library/Icons"; + +NSSize WebIconSmallSize = {16, 16}; +NSSize WebIconMediumSize = {32, 32}; +NSSize WebIconLargeSize = {128, 128}; + +#define UniqueFilePathSize (34) + +static WebIconDatabaseClient* defaultClient() +{ + static WebIconDatabaseClient* defaultClient = new WebIconDatabaseClient(); + return defaultClient; +} + +@interface WebIconDatabase (WebReallyInternal) +- (BOOL)_isEnabled; +- (void)_sendNotificationForURL:(NSString *)URL; +- (void)_sendDidRemoveAllIconsNotification; +- (NSImage *)_iconForFileURL:(NSString *)fileURL withSize:(NSSize)size; +- (void)_resetCachedWebPreferences:(NSNotification *)notification; +- (NSImage *)_largestIconFromDictionary:(NSMutableDictionary *)icons; +- (NSMutableDictionary *)_iconsBySplittingRepresentationsOfIcon:(NSImage *)icon; +- (NSImage *)_iconFromDictionary:(NSMutableDictionary *)icons forSize:(NSSize)size cache:(BOOL)cache; +- (void)_scaleIcon:(NSImage *)icon toSize:(NSSize)size; +- (NSString *)_databaseDirectory; +@end + +@implementation WebIconDatabase + ++ (WebIconDatabase *)sharedIconDatabase +{ + static WebIconDatabase *database = nil; + if (!database) + database = [[WebIconDatabase alloc] init]; + return database; +} + +- init +{ + [super init]; + WebCoreThreadViolationCheck(); + + _private = [[WebIconDatabasePrivate alloc] init]; + + // Check the user defaults and see if the icon database should even be enabled. + // Inform the bridge and, if we're disabled, bail from init right here + NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults]; + // <rdar://problem/4741419> - IconDatabase should be disabled by default + NSDictionary *initialDefaults = [[NSDictionary alloc] initWithObjectsAndKeys:[NSNumber numberWithBool:YES], WebIconDatabaseEnabledDefaultsKey, nil]; + [defaults registerDefaults:initialDefaults]; + [initialDefaults release]; + BOOL enabled = [defaults boolForKey:WebIconDatabaseEnabledDefaultsKey]; + iconDatabase()->setEnabled(enabled); + if (!enabled) + return self; + iconDatabase()->setClient(defaultClient()); + + // Figure out the directory we should be using for the icon.db + NSString *databaseDirectory = [self _databaseDirectory]; + + // Rename legacy icon database files to the new icon database name + BOOL isDirectory = NO; + NSString *legacyDB = [databaseDirectory stringByAppendingPathComponent:@"icon.db"]; + NSFileManager *defaultManager = [NSFileManager defaultManager]; + if ([defaultManager fileExistsAtPath:legacyDB isDirectory:&isDirectory] && !isDirectory) { + NSString *newDB = [databaseDirectory stringByAppendingPathComponent:iconDatabase()->defaultDatabaseFilename()]; + if (![defaultManager fileExistsAtPath:newDB]) + rename([legacyDB fileSystemRepresentation], [newDB fileSystemRepresentation]); + } + + // Set the private browsing pref then open the WebCore icon database + iconDatabase()->setPrivateBrowsingEnabled([[WebPreferences standardPreferences] privateBrowsingEnabled]); + if (!iconDatabase()->open(databaseDirectory)) + LOG_ERROR("Unable to open icon database"); + + // Register for important notifications + [[NSNotificationCenter defaultCenter] addObserver:self + selector:@selector(_applicationWillTerminate:) + name:NSApplicationWillTerminateNotification + object:NSApp]; + [[NSNotificationCenter defaultCenter] + addObserver:self selector:@selector(_resetCachedWebPreferences:) + name:WebPreferencesChangedNotification object:nil]; + + return self; +} + +- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size cache:(BOOL)cache +{ + ASSERT_MAIN_THREAD(); + ASSERT(size.width); + ASSERT(size.height); + + if (!URL || ![self _isEnabled]) + return [self defaultIconForURL:URL withSize:size]; + + // FIXME - <rdar://problem/4697934> - Move the handling of FileURLs to WebCore and implement in ObjC++ + if ([URL _webkit_isFileURL]) + return [self _iconForFileURL:URL withSize:size]; + + if (Image* image = iconDatabase()->iconForPageURL(URL, IntSize(size))) + if (NSImage *icon = webGetNSImage(image, size)) + return icon; + return [self defaultIconForURL:URL withSize:size]; +} + +- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size +{ + return [self iconForURL:URL withSize:size cache:YES]; +} + +- (NSString *)iconURLForURL:(NSString *)URL +{ + if (![self _isEnabled]) + return nil; + ASSERT_MAIN_THREAD(); + + return iconDatabase()->iconURLForPageURL(URL); +} + +- (NSImage *)defaultIconWithSize:(NSSize)size +{ + ASSERT_MAIN_THREAD(); + ASSERT(size.width); + ASSERT(size.height); + + Image* image = iconDatabase()->defaultIcon(IntSize(size)); + return image ? image->getNSImage() : nil; +} + +- (NSImage *)defaultIconForURL:(NSString *)URL withSize:(NSSize)size +{ + if (_private->delegateImplementsDefaultIconForURL) + return [_private->delegate webIconDatabase:self defaultIconForURL:URL withSize:size]; + return [self defaultIconWithSize:size]; +} + +- (void)retainIconForURL:(NSString *)URL +{ + ASSERT_MAIN_THREAD(); + ASSERT(URL); + if (![self _isEnabled]) + return; + + iconDatabase()->retainIconForPageURL(URL); +} + +- (void)releaseIconForURL:(NSString *)pageURL +{ + ASSERT_MAIN_THREAD(); + ASSERT(pageURL); + if (![self _isEnabled]) + return; + + iconDatabase()->releaseIconForPageURL(pageURL); +} + ++ (void)delayDatabaseCleanup +{ + ASSERT_MAIN_THREAD(); + + IconDatabase::delayDatabaseCleanup(); +} + ++ (void)allowDatabaseCleanup +{ + ASSERT_MAIN_THREAD(); + + IconDatabase::allowDatabaseCleanup(); +} + +- (void)setDelegate:(id)delegate +{ + _private->delegate = delegate; + _private->delegateImplementsDefaultIconForURL = [delegate respondsToSelector:@selector(webIconDatabase:defaultIconForURL:withSize:)]; +} + +- (id)delegate +{ + return _private->delegate; +} + +@end + + +@implementation WebIconDatabase (WebPendingPublic) + +- (void)removeAllIcons +{ + ASSERT_MAIN_THREAD(); + if (![self _isEnabled]) + return; + + // Via the IconDatabaseClient interface, removeAllIcons() will send the WebIconDatabaseDidRemoveAllIconsNotification + iconDatabase()->removeAllIcons(); +} + +@end + +@implementation WebIconDatabase (WebPrivate) + ++ (void)_checkIntegrityBeforeOpening +{ + iconDatabase()->checkIntegrityBeforeOpening(); +} + +@end + +@implementation WebIconDatabase (WebInternal) + +- (BOOL)_isEnabled +{ + return iconDatabase()->isEnabled(); +} + +- (void)_sendNotificationForURL:(NSString *)URL +{ + ASSERT(URL); + + NSDictionary *userInfo = [NSDictionary dictionaryWithObject:URL + forKey:WebIconNotificationUserInfoURLKey]; + + [[NSNotificationCenter defaultCenter] postNotificationOnMainThreadWithName:WebIconDatabaseDidAddIconNotification + object:self + userInfo:userInfo]; +} + +- (void)_sendDidRemoveAllIconsNotification +{ + [[NSNotificationCenter defaultCenter] postNotificationOnMainThreadWithName:WebIconDatabaseDidRemoveAllIconsNotification + object:self + userInfo:nil]; +} + +- (void)_applicationWillTerminate:(NSNotification *)notification +{ + iconDatabase()->close(); +} + +- (NSImage *)_iconForFileURL:(NSString *)file withSize:(NSSize)size +{ + ASSERT_MAIN_THREAD(); + ASSERT(size.width); + ASSERT(size.height); + + NSWorkspace *workspace = [NSWorkspace sharedWorkspace]; + NSString *path = [[NSURL _web_URLWithDataAsString:file] path]; + NSString *suffix = [path pathExtension]; + NSImage *icon = nil; + + if ([suffix _webkit_isCaseInsensitiveEqualToString:@"htm"] || [suffix _webkit_isCaseInsensitiveEqualToString:@"html"]) { + if (!_private->htmlIcons) { + icon = [workspace iconForFileType:@"html"]; + _private->htmlIcons = [[self _iconsBySplittingRepresentationsOfIcon:icon] retain]; + } + icon = [self _iconFromDictionary:_private->htmlIcons forSize:size cache:YES]; + } else { + if (!path || ![path isAbsolutePath]) { + // Return the generic icon when there is no path. + icon = [workspace iconForFileType:NSFileTypeForHFSTypeCode(kGenericDocumentIcon)]; + } else { + icon = [workspace iconForFile:path]; + } + [self _scaleIcon:icon toSize:size]; + } + + return icon; +} + +- (void)_resetCachedWebPreferences:(NSNotification *)notification +{ + BOOL privateBrowsingEnabledNow = [[WebPreferences standardPreferences] privateBrowsingEnabled]; + iconDatabase()->setPrivateBrowsingEnabled(privateBrowsingEnabledNow); +} + +- (NSImage *)_largestIconFromDictionary:(NSMutableDictionary *)icons +{ + ASSERT(icons); + + NSEnumerator *enumerator = [icons keyEnumerator]; + NSValue *currentSize, *largestSize=nil; + float largestSizeArea=0; + + while ((currentSize = [enumerator nextObject]) != nil) { + NSSize currentSizeSize = [currentSize sizeValue]; + float currentSizeArea = currentSizeSize.width * currentSizeSize.height; + if(!largestSizeArea || (currentSizeArea > largestSizeArea)){ + largestSize = currentSize; + largestSizeArea = currentSizeArea; + } + } + + return [icons objectForKey:largestSize]; +} + +- (NSMutableDictionary *)_iconsBySplittingRepresentationsOfIcon:(NSImage *)icon +{ + ASSERT(icon); + + NSMutableDictionary *icons = [NSMutableDictionary dictionary]; + NSEnumerator *enumerator = [[icon representations] objectEnumerator]; + NSImageRep *rep; + + while ((rep = [enumerator nextObject]) != nil) { + NSSize size = [rep size]; + NSImage *subIcon = [[NSImage alloc] initWithSize:size]; + [subIcon addRepresentation:rep]; + [icons setObject:subIcon forKey:[NSValue valueWithSize:size]]; + [subIcon release]; + } + + if([icons count] > 0) + return icons; + + LOG_ERROR("icon has no representations"); + + return nil; +} + +- (NSImage *)_iconFromDictionary:(NSMutableDictionary *)icons forSize:(NSSize)size cache:(BOOL)cache +{ + ASSERT(size.width); + ASSERT(size.height); + + NSImage *icon = [icons objectForKey:[NSValue valueWithSize:size]]; + + if(!icon){ + icon = [[[self _largestIconFromDictionary:icons] copy] autorelease]; + [self _scaleIcon:icon toSize:size]; + + if(cache){ + [icons setObject:icon forKey:[NSValue valueWithSize:size]]; + } + } + + return icon; +} + +- (void)_scaleIcon:(NSImage *)icon toSize:(NSSize)size +{ + ASSERT(size.width); + ASSERT(size.height); + +#if !LOG_DISABLED + double start = CFAbsoluteTimeGetCurrent(); +#endif + + [icon setScalesWhenResized:YES]; + [icon setSize:size]; + +#if !LOG_DISABLED + double duration = CFAbsoluteTimeGetCurrent() - start; + LOG(Timing, "scaling icon took %f seconds.", duration); +#endif +} + +// This hashing String->filename algorithm came from WebFileDatabase.m and is what was used in the +// WebKit Icon Database +static void legacyIconDatabaseFilePathForKey(id key, char *buffer) +{ + const char *s; + UInt32 hash1; + UInt32 hash2; + CFIndex len; + CFIndex cnt; + + s = [[[[key description] lowercaseString] stringByStandardizingPath] UTF8String]; + len = strlen(s); + + // compute first hash + hash1 = len; + for (cnt = 0; cnt < len; cnt++) { + hash1 += (hash1 << 8) + s[cnt]; + } + hash1 += (hash1 << (len & 31)); + + // compute second hash + hash2 = len; + for (cnt = 0; cnt < len; cnt++) { + hash2 = (37 * hash2) ^ s[cnt]; + } + +#ifdef __LP64__ + snprintf(buffer, UniqueFilePathSize, "%.2u/%.2u/%.10u-%.10u.cache", ((hash1 & 0xff) >> 4), ((hash2 & 0xff) >> 4), hash1, hash2); +#else + snprintf(buffer, UniqueFilePathSize, "%.2lu/%.2lu/%.10lu-%.10lu.cache", ((hash1 & 0xff) >> 4), ((hash2 & 0xff) >> 4), hash1, hash2); +#endif +} + +// This method of getting an object from the filesystem is taken from the old +// WebKit Icon Database +static id objectFromPathForKey(NSString *databasePath, id key) +{ + ASSERT(key); + id result = nil; + + // Use the key->filename hashing the old WebKit IconDatabase used + char uniqueKey[UniqueFilePathSize]; + legacyIconDatabaseFilePathForKey(key, uniqueKey); + + // Get the data from this file and setup for the un-archiving + NSString *filePath = [[NSString alloc] initWithFormat:@"%@/%s", databasePath, uniqueKey]; + NSData *data = [[NSData alloc] initWithContentsOfFile:filePath]; + NSUnarchiver *unarchiver = nil; + + @try { + if (data) { + unarchiver = [[NSUnarchiver alloc] initForReadingWithData:data]; + if (unarchiver) { + id fileKey = [unarchiver decodeObject]; + if ([fileKey isEqual:key]) { + id object = [unarchiver decodeObject]; + if (object) { + // Decoded objects go away when the unarchiver does, so we need to + // retain this so we can return it to our caller. + result = [[object retain] autorelease]; + LOG(IconDatabase, "read disk cache file - %@", key); + } + } + } + } + } @catch (NSException *localException) { + LOG(IconDatabase, "cannot unarchive cache file - %@", key); + result = nil; + } + + [unarchiver release]; + [data release]; + [filePath release]; + + return result; +} + +static NSData* iconDataFromPathForIconURL(NSString *databasePath, NSString *iconURLString) +{ + ASSERT(iconURLString); + ASSERT(databasePath); + + NSData *iconData = objectFromPathForKey(databasePath, iconURLString); + + if ((id)iconData == (id)[NSNull null]) + return nil; + + return iconData; +} + +- (NSString *)_databaseDirectory +{ + NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults]; + + // Figure out the directory we should be using for the icon.db + NSString *databaseDirectory = [defaults objectForKey:WebIconDatabaseDirectoryDefaultsKey]; + if (!databaseDirectory) { + databaseDirectory = WebIconDatabasePath; + [defaults setObject:databaseDirectory forKey:WebIconDatabaseDirectoryDefaultsKey]; + } + + return [[databaseDirectory stringByExpandingTildeInPath] stringByStandardizingPath]; +} + +@end + +@implementation WebIconDatabasePrivate +@end + +@interface ThreadEnabler : NSObject { +} ++ (void)enableThreading; + +- (void)threadEnablingSelector:(id)arg; +@end + +@implementation ThreadEnabler + +- (void)threadEnablingSelector:(id)arg +{ + return; +} + ++ (void)enableThreading +{ + ThreadEnabler *enabler = [[ThreadEnabler alloc] init]; + [NSThread detachNewThreadSelector:@selector(threadEnablingSelector:) toTarget:enabler withObject:nil]; + [enabler release]; +} + +@end + +bool importToWebCoreFormat() +{ + // Since this is running on a secondary POSIX thread and Cocoa cannot be used multithreaded unless an NSThread has been detached, + // make sure that happens here for all WebKit clients + if (![NSThread isMultiThreaded]) + [ThreadEnabler enableThreading]; + ASSERT([NSThread isMultiThreaded]); + +#ifndef BUILDING_ON_TIGER + // Tell backup software (i.e., Time Machine) to never back up the icon database, because + // it's a large file that changes frequently, thus using a lot of backup disk space, and + // it's unlikely that many users would be upset about it not being backed up. We do this + // here because this code is only executed once for each icon database instance. We could + // make this configurable on a per-client basis someday if that seemed useful. + // See <rdar://problem/5320208>. + CFStringRef databasePath = iconDatabase()->databasePath().createCFString(); + if (databasePath) { + CFURLRef databasePathURL = CFURLCreateWithFileSystemPath(0, databasePath, kCFURLPOSIXPathStyle, FALSE); + CFRelease(databasePath); + CSBackupSetItemExcluded(databasePathURL, true, true); + CFRelease(databasePathURL); + } +#endif + + // Get the directory the old icon database *should* be in + NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults]; + NSString *databaseDirectory = [defaults objectForKey:WebIconDatabaseImportDirectoryDefaultsKey]; + + if (!databaseDirectory) + databaseDirectory = [defaults objectForKey:WebIconDatabaseDirectoryDefaultsKey]; + + if (!databaseDirectory) { + databaseDirectory = WebIconDatabasePath; + [defaults setObject:databaseDirectory forKey:WebIconDatabaseDirectoryDefaultsKey]; + } + databaseDirectory = [databaseDirectory stringByExpandingTildeInPath]; + + // With this directory, get the PageURLToIconURL map that was saved to disk + NSMutableDictionary *pageURLToIconURL = objectFromPathForKey(databaseDirectory, WebURLToIconURLKey); + + // If the retrieved object was not a valid NSMutableDictionary, then we have no valid + // icons to import + if (![pageURLToIconURL isKindOfClass:[NSMutableDictionary class]]) + pageURLToIconURL = nil; + + NSEnumerator *enumerator = [pageURLToIconURL keyEnumerator]; + NSString *url, *iconURL; + + // First, we'll iterate through the PageURL->IconURL map + while ((url = [enumerator nextObject]) != nil) { + iconURL = [pageURLToIconURL objectForKey:url]; + if (!iconURL) + continue; + iconDatabase()->importIconURLForPageURL(iconURL, url); + if (iconDatabase()->shouldStopThreadActivity()) + return false; + } + + // Second, we'll get a list of the unique IconURLs we have + NSMutableSet *iconsOnDiskWithURLs = [NSMutableSet setWithArray:[pageURLToIconURL allValues]]; + enumerator = [iconsOnDiskWithURLs objectEnumerator]; + NSData *iconData; + + // And iterate through them, adding the icon data to the new icon database + while ((url = [enumerator nextObject]) != nil) { + iconData = iconDataFromPathForIconURL(databaseDirectory, url); + if (iconData) + iconDatabase()->importIconDataForIconURL(SharedBuffer::wrapNSData(iconData), url); + else { + // This really *shouldn't* happen, so it'd be good to track down why it might happen in a debug build + // however, we do know how to handle it gracefully in release + LOG_ERROR("%@ is marked as having an icon on disk, but we couldn't get the data for it", url); + iconDatabase()->importIconDataForIconURL(0, url); + } + if (iconDatabase()->shouldStopThreadActivity()) + return false; + } + + // After we're done importing old style icons over to webcore icons, we delete the entire directory hierarchy + // for the old icon DB (skipping the new iconDB if it is in the same directory) + NSFileManager *fileManager = [NSFileManager defaultManager]; + enumerator = [[fileManager contentsOfDirectoryAtPath:databaseDirectory error:NULL] objectEnumerator]; + + NSString *databaseFilename = iconDatabase()->defaultDatabaseFilename(); + + BOOL foundIconDB = NO; + NSString *file; + while ((file = [enumerator nextObject]) != nil) { + if ([file caseInsensitiveCompare:databaseFilename] == NSOrderedSame) { + foundIconDB = YES; + continue; + } + NSString *filePath = [databaseDirectory stringByAppendingPathComponent:file]; + if (![fileManager removeItemAtPath:filePath error:NULL]) + LOG_ERROR("Failed to delete %@ from old icon directory", filePath); + } + + // If the new iconDB wasn't in that directory, we can delete the directory itself + if (!foundIconDB) + rmdir([databaseDirectory fileSystemRepresentation]); + + return true; +} + +NSImage *webGetNSImage(Image* image, NSSize size) +{ + ASSERT_MAIN_THREAD(); + ASSERT(size.width); + ASSERT(size.height); + + // FIXME: We're doing the resize here for now because WebCore::Image doesn't yet support resizing/multiple representations + // This makes it so there's effectively only one size of a particular icon in the system at a time. We should move this + // to WebCore::Image at some point. + if (!image) + return nil; + NSImage* nsImage = image->getNSImage(); + if (!nsImage) + return nil; + if (!NSEqualSizes([nsImage size], size)) { + [nsImage setScalesWhenResized:YES]; + [nsImage setSize:size]; + } + return nsImage; +} diff --git a/WebKit/mac/Misc/WebIconDatabaseDelegate.h b/WebKit/mac/Misc/WebIconDatabaseDelegate.h new file mode 100644 index 0000000..ad6aed2 --- /dev/null +++ b/WebKit/mac/Misc/WebIconDatabaseDelegate.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +@interface NSObject (WebIconDatabaseDelegate) + +- (NSImage *)webIconDatabase:(WebIconDatabase *)webIconDatabase defaultIconForURL:(NSString *)URL withSize:(NSSize)size; + +@end + + diff --git a/WebKit/mac/Misc/WebIconDatabaseInternal.h b/WebKit/mac/Misc/WebIconDatabaseInternal.h new file mode 100644 index 0000000..b7b01ec --- /dev/null +++ b/WebKit/mac/Misc/WebIconDatabaseInternal.h @@ -0,0 +1,49 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebIconDatabasePrivate.h" + +namespace WebCore { + class Image; +} + +@interface WebIconDatabasePrivate : NSObject { +@public + id delegate; + BOOL delegateImplementsDefaultIconForURL; + NSMutableDictionary *htmlIcons; +} +@end + +@interface WebIconDatabase (WebInternal) +- (void)_sendNotificationForURL:(NSString *)URL; +- (void)_sendDidRemoveAllIconsNotification; +@end + +extern bool importToWebCoreFormat(); +NSImage *webGetNSImage(WebCore::Image*, NSSize); diff --git a/WebKit/mac/Misc/WebIconDatabasePrivate.h b/WebKit/mac/Misc/WebIconDatabasePrivate.h new file mode 100644 index 0000000..aff923e --- /dev/null +++ b/WebKit/mac/Misc/WebIconDatabasePrivate.h @@ -0,0 +1,59 @@ +/* + * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebIconDatabase.h> + +// FIXME: Some of the following is not API and should be moved +// either inside WebIconDatabase.mm, or to WebIconDatabaseInternal.h. + +// Sent when all icons are removed from the database. The object of the notification is +// the icon database. There is no userInfo. Clients should react by removing any cached +// icon images from the user interface. Clients need not and should not call +// releaseIconForURL: in response to this notification. +extern NSString *WebIconDatabaseDidRemoveAllIconsNotification; + +// Key to store the path to look for old style icons in to convert to the new icon db +extern NSString *WebIconDatabaseImportDirectoryDefaultsKey; + +@interface WebIconDatabase (WebPendingPublic) + +/*! + @method removeAllIcons: + @discussion Causes the icon database to delete all of the images that it has stored, + and to send out the notification WebIconDatabaseDidRemoveAllIconsNotification. +*/ +- (void)removeAllIcons; + +@end + +@interface WebIconDatabase (WebPrivate) + ++ (void)_checkIntegrityBeforeOpening; + +@end + diff --git a/WebKit/mac/Misc/WebIconFetcher.h b/WebKit/mac/Misc/WebIconFetcher.h new file mode 100644 index 0000000..d27ad94 --- /dev/null +++ b/WebKit/mac/Misc/WebIconFetcher.h @@ -0,0 +1,36 @@ +/* + * Copyright (C) 2008 Apple Inc. All Rights Reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + +@class WebIconFetcherPrivate; + +@interface WebIconFetcher : NSObject { + WebIconFetcherPrivate *_private; +} + +- (void)cancel; + +@end diff --git a/WebKit/mac/Misc/WebIconFetcher.mm b/WebKit/mac/Misc/WebIconFetcher.mm new file mode 100644 index 0000000..bec7c12 --- /dev/null +++ b/WebKit/mac/Misc/WebIconFetcher.mm @@ -0,0 +1,126 @@ +/* + * Copyright (C) 2008 Apple Inc. All Rights Reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebIconFetcher.h" + +#import "WebFrameInternal.h" +#import "WebIconFetcherInternal.h" + +#import <WebCore/Frame.h> +#import <WebCore/IconFetcher.h> +#import <WebCore/SharedBuffer.h> +#import <wtf/PassRefPtr.h> + +using namespace WebCore; + +class WebIconFetcherClient : public IconFetcherClient { +public: + WebIconFetcherClient(id target, SEL selector) + : m_target(target) + , m_selector(selector) + { + } + + virtual void finishedFetchingIcon(PassRefPtr<SharedBuffer> iconData) + { + RetainPtr<NSData> data; + if (iconData) + data = iconData->createNSData(); + + [m_target performSelector:m_selector withObject:m_fetcher.get() withObject:data.get()]; + + delete this; + } + + void setFetcher(WebIconFetcher *fetcher) { m_fetcher = fetcher; } + +private: + RetainPtr<WebIconFetcher> m_fetcher; + id m_target; + SEL m_selector; +}; + +@implementation WebIconFetcher + +- (id)init +{ + return nil; +} + +- (void)dealloc +{ + reinterpret_cast<IconFetcher*>(_private)->deref(); + + [super dealloc]; +} + +- (void)finalize +{ + reinterpret_cast<IconFetcher*>(_private)->deref(); + + [super finalize]; +} + +- (void)cancel +{ + reinterpret_cast<IconFetcher*>(_private)->cancel(); +} + +@end + +@implementation WebIconFetcher (WebInternal) + +- (id)_initWithIconFetcher:(PassRefPtr<IconFetcher>)iconFetcher client:(WebIconFetcherClient *)client +{ + ASSERT(iconFetcher); + + self = [super init]; + if (!self) + return nil; + + client->setFetcher(self); + _private = reinterpret_cast<WebIconFetcherPrivate*>(iconFetcher.releaseRef()); + + return self; +} + ++ (WebIconFetcher *)_fetchApplicationIconForFrame:(WebFrame *)webFrame + target:(id)target + selector:(SEL)selector +{ + Frame* frame = core(webFrame); + + WebIconFetcherClient* client = new WebIconFetcherClient(target, selector); + + RefPtr<IconFetcher> fetcher = IconFetcher::create(frame, client); + + if (!fetcher) + return nil; + + return [[[WebIconFetcher alloc] _initWithIconFetcher:fetcher.release() client:client] autorelease]; +} + +@end + diff --git a/WebKit/mac/Misc/WebIconFetcherInternal.h b/WebKit/mac/Misc/WebIconFetcherInternal.h new file mode 100644 index 0000000..5951ef9 --- /dev/null +++ b/WebKit/mac/Misc/WebIconFetcherInternal.h @@ -0,0 +1,42 @@ +/* + * Copyright (C) 2008 Apple Inc. All Rights Reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY + * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebIconFetcher.h> +#import <wtf/Forward.h> + +namespace WebCore { + class IconFetcher; +} + +@class WebFrame; + +@interface WebIconFetcher (WebInternal) + ++ (WebIconFetcher *)_fetchApplicationIconForFrame:(WebFrame *)webFrame + target:(id)target + selector:(SEL)selector; + +@end + diff --git a/WebKit/mac/Misc/WebKit.h b/WebKit/mac/Misc/WebKit.h new file mode 100644 index 0000000..84bfd37 --- /dev/null +++ b/WebKit/mac/Misc/WebKit.h @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2003, 2004 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/DOM.h> +#import <WebKit/WebArchive.h> +#import <WebKit/WebBackForwardList.h> +#import <WebKit/WebDataSource.h> +#import <WebKit/WebDocument.h> +#import <WebKit/WebDOMOperations.h> +#import <WebKit/WebDownload.h> +#import <WebKit/WebEditingDelegate.h> +#import <WebKit/WebFrame.h> +#import <WebKit/WebFrameLoadDelegate.h> +#import <WebKit/WebFrameView.h> +#import <WebKit/WebHistory.h> +#import <WebKit/WebHistoryItem.h> +#import <WebKit/WebKitErrors.h> +#import <WebKit/WebPlugin.h> +#import <WebKit/WebPluginContainer.h> +#import <WebKit/WebPluginViewFactory.h> +#import <WebKit/WebPolicyDelegate.h> +#import <WebKit/WebPreferences.h> +#import <WebKit/WebResource.h> +#import <WebKit/WebResourceLoadDelegate.h> +#import <WebKit/WebScriptObject.h> +#import <WebKit/WebUIDelegate.h> +#import <WebKit/WebView.h> diff --git a/WebKit/mac/Misc/WebKitErrors.h b/WebKit/mac/Misc/WebKitErrors.h new file mode 100644 index 0000000..e4cbdcc --- /dev/null +++ b/WebKit/mac/Misc/WebKitErrors.h @@ -0,0 +1,59 @@ +/* + * Copyright (C) 2003 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +extern NSString *WebKitErrorDomain; + +extern NSString * const WebKitErrorMIMETypeKey; +extern NSString * const WebKitErrorPlugInNameKey; +extern NSString * const WebKitErrorPlugInPageURLStringKey; + +/*! + @enum + @abstract Policy errors + @constant WebKitErrorCannotShowMIMEType + @constant WebKitErrorCannotShowURL + @constant WebKitErrorFrameLoadInterruptedByPolicyChange +*/ +enum { + WebKitErrorCannotShowMIMEType = 100, + WebKitErrorCannotShowURL = 101, + WebKitErrorFrameLoadInterruptedByPolicyChange = 102, +}; + +/*! + @enum + @abstract Plug-in and java errors + @constant WebKitErrorCannotFindPlugIn + @constant WebKitErrorCannotLoadPlugIn + @constant WebKitErrorJavaUnavailable +*/ +enum { + WebKitErrorCannotFindPlugIn = 200, + WebKitErrorCannotLoadPlugIn = 201, + WebKitErrorJavaUnavailable = 202, +}; diff --git a/WebKit/mac/Misc/WebKitErrors.m b/WebKit/mac/Misc/WebKitErrors.m new file mode 100644 index 0000000..fc739ba --- /dev/null +++ b/WebKit/mac/Misc/WebKitErrors.m @@ -0,0 +1,167 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebKitErrors.h> + +#import <WebKit/WebKitErrorsPrivate.h> +#import <WebKit/WebLocalizableStrings.h> +#import <WebKit/WebNSURLExtras.h> + +#import <pthread.h> + +NSString *WebKitErrorDomain = @"WebKitErrorDomain"; + +NSString * const WebKitErrorMIMETypeKey = @"WebKitErrorMIMETypeKey"; +NSString * const WebKitErrorPlugInNameKey = @"WebKitErrorPlugInNameKey"; +NSString * const WebKitErrorPlugInPageURLStringKey = @"WebKitErrorPlugInPageURLStringKey"; + +// Policy errors +#define WebKitErrorDescriptionCannotShowMIMEType UI_STRING("Cannot show content with specified mime type", "WebKitErrorCannotShowMIMEType description") +#define WebKitErrorDescriptionCannotShowURL UI_STRING("Cannot show URL", "WebKitErrorCannotShowURL description") +#define WebKitErrorDescriptionFrameLoadInterruptedByPolicyChange UI_STRING("Frame load interrupted", "WebKitErrorFrameLoadInterruptedByPolicyChange description") +#define WebKitErrorDescriptionCannotUseRestrictedPort UI_STRING("Not allowed to use restricted network port", "WebKitErrorCannotUseRestrictedPort description") + +// Plug-in and java errors +#define WebKitErrorDescriptionCannotFindPlugin UI_STRING("Cannot find plug-in", "WebKitErrorCannotFindPlugin description") +#define WebKitErrorDescriptionCannotLoadPlugin UI_STRING("Cannot load plug-in", "WebKitErrorCannotLoadPlugin description") +#define WebKitErrorDescriptionJavaUnavailable UI_STRING("Java is unavailable", "WebKitErrorJavaUnavailable description") +#define WebKitErrorDescriptionPlugInCancelledConnection UI_STRING("Plug-in cancelled", "WebKitErrorPlugInCancelledConnection description") +#define WebKitErrorDescriptionPlugInWillHandleLoad UI_STRING("Plug-in handled load", "WebKitErrorPlugInWillHandleLoad description") + +static pthread_once_t registerErrorsControl = PTHREAD_ONCE_INIT; +static void registerErrors(void); + +@implementation NSError (WebKitExtras) + +static NSMutableDictionary *descriptions = nil; + ++ (void)_registerWebKitErrors +{ + pthread_once(®isterErrorsControl, registerErrors); +} + +-(id)_webkit_initWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL +{ + NSDictionary *descriptionsDict; + NSString *localizedDesc; + NSDictionary *dict; + // insert a localized string here for those folks not savvy to our category methods + descriptionsDict = [descriptions objectForKey:domain]; + localizedDesc = descriptionsDict ? [descriptionsDict objectForKey:[NSNumber numberWithInt:code]] : nil; + dict = [NSDictionary dictionaryWithObjectsAndKeys: + URL, @"NSErrorFailingURLKey", + [URL absoluteString], @"NSErrorFailingURLStringKey", + localizedDesc, NSLocalizedDescriptionKey, + nil]; + return [self initWithDomain:domain code:code userInfo:dict]; +} + ++(id)_webkit_errorWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL +{ + return [[[self alloc] _webkit_initWithDomain:domain code:code URL:URL] autorelease]; +} + ++ (NSError *)_webKitErrorWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL +{ + [self _registerWebKitErrors]; + return [self _webkit_errorWithDomain:domain code:code URL:URL]; +} + ++ (NSError *)_webKitErrorWithCode:(int)code failingURL:(NSString *)URLString +{ + return [self _webKitErrorWithDomain:WebKitErrorDomain code:code URL:[NSURL _web_URLWithUserTypedString:URLString]]; +} + +- (id)_initWithPluginErrorCode:(int)code + contentURL:(NSURL *)contentURL + pluginPageURL:(NSURL *)pluginPageURL + pluginName:(NSString *)pluginName + MIMEType:(NSString *)MIMEType +{ + [[self class] _registerWebKitErrors]; + + NSMutableDictionary *userInfo = [[NSMutableDictionary alloc] init]; + if (contentURL) { + [userInfo setObject:contentURL forKey:@"NSErrorFailingURLKey"]; +#if defined(BUILDING_ON_TIGER) || defined(BUILDING_ON_LEOPARD) + [userInfo setObject:[contentURL _web_userVisibleString] forKey:NSErrorFailingURLStringKey]; +#else + [userInfo setObject:[contentURL _web_userVisibleString] forKey:NSURLErrorFailingURLStringErrorKey]; +#endif + } + if (pluginPageURL) { + [userInfo setObject:[pluginPageURL _web_userVisibleString] forKey:WebKitErrorPlugInPageURLStringKey]; + } + if (pluginName) { + [userInfo setObject:pluginName forKey:WebKitErrorPlugInNameKey]; + } + if (MIMEType) { + [userInfo setObject:MIMEType forKey:WebKitErrorMIMETypeKey]; + } + + NSDictionary *userInfoCopy = [userInfo count] > 0 ? [[NSDictionary alloc] initWithDictionary:userInfo] : nil; + [userInfo release]; + NSError *error = [self initWithDomain:WebKitErrorDomain code:code userInfo:userInfoCopy]; + [userInfoCopy release]; + + return error; +} + ++ (void)_webkit_addErrorsWithCodesAndDescriptions:(NSDictionary *)dictionary inDomain:(NSString *)domain +{ + if (!descriptions) + descriptions = [[NSMutableDictionary alloc] init]; + + [descriptions setObject:dictionary forKey:domain]; +} + +static void registerErrors() +{ + NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; + + NSDictionary *dict = [NSDictionary dictionaryWithObjectsAndKeys: + // Policy errors + WebKitErrorDescriptionCannotShowMIMEType, [NSNumber numberWithInt: WebKitErrorCannotShowMIMEType], + WebKitErrorDescriptionCannotShowURL, [NSNumber numberWithInt: WebKitErrorCannotShowURL], + WebKitErrorDescriptionFrameLoadInterruptedByPolicyChange, [NSNumber numberWithInt: WebKitErrorFrameLoadInterruptedByPolicyChange], + WebKitErrorDescriptionCannotUseRestrictedPort, [NSNumber numberWithInt: WebKitErrorCannotUseRestrictedPort], + + // Plug-in and java errors + WebKitErrorDescriptionCannotFindPlugin, [NSNumber numberWithInt: WebKitErrorCannotFindPlugIn], + WebKitErrorDescriptionCannotLoadPlugin, [NSNumber numberWithInt: WebKitErrorCannotLoadPlugIn], + WebKitErrorDescriptionJavaUnavailable, [NSNumber numberWithInt: WebKitErrorJavaUnavailable], + WebKitErrorDescriptionPlugInCancelledConnection, [NSNumber numberWithInt: WebKitErrorPlugInCancelledConnection], + WebKitErrorDescriptionPlugInWillHandleLoad, [NSNumber numberWithInt: WebKitErrorPlugInWillHandleLoad], + nil]; + + [NSError _webkit_addErrorsWithCodesAndDescriptions:dict inDomain:WebKitErrorDomain]; + + [pool drain]; +} + +@end diff --git a/WebKit/mac/Misc/WebKitErrorsPrivate.h b/WebKit/mac/Misc/WebKitErrorsPrivate.h new file mode 100644 index 0000000..6a98c4e --- /dev/null +++ b/WebKit/mac/Misc/WebKitErrorsPrivate.h @@ -0,0 +1,53 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebKitErrors.h> + +#define WebKitErrorPlugInCancelledConnection 203 +// FIXME: WebKitErrorPlugInWillHandleLoad is used for the cancel we do to prevent loading plugin content twice. See <rdar://problem/4258008> +#define WebKitErrorPlugInWillHandleLoad 204 + +/*! + @enum + @abstract Policy errors - Pending Public API Review + @constant WebKitErrorCannotUseRestrictedPort +*/ +enum { + WebKitErrorCannotUseRestrictedPort = 103, +}; + +@interface NSError (WebKitExtras) ++ (NSError *)_webKitErrorWithCode:(int)code failingURL:(NSString *)URL; ++ (NSError *)_webKitErrorWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL; + +- (id)_initWithPluginErrorCode:(int)code + contentURL:(NSURL *)contentURL + pluginPageURL:(NSURL *)pluginPageURL + pluginName:(NSString *)pluginName + MIMEType:(NSString *)MIMEType; +@end diff --git a/WebKit/mac/Misc/WebKitLogging.h b/WebKit/mac/Misc/WebKitLogging.h new file mode 100644 index 0000000..dc37dbf --- /dev/null +++ b/WebKit/mac/Misc/WebKitLogging.h @@ -0,0 +1,85 @@ +/* + * Copyright (C) 2005, 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <wtf/Assertions.h> + +#ifndef LOG_CHANNEL_PREFIX +#define LOG_CHANNEL_PREFIX WebKitLog +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern WTFLogChannel WebKitLogTiming; +extern WTFLogChannel WebKitLogLoading; +extern WTFLogChannel WebKitLogFontCache; +extern WTFLogChannel WebKitLogFontSubstitution; +extern WTFLogChannel WebKitLogFontSelection; +extern WTFLogChannel WebKitLogDownload; +extern WTFLogChannel WebKitLogDocumentLoad; +extern WTFLogChannel WebKitLogPlugins; +extern WTFLogChannel WebKitLogEvents; +extern WTFLogChannel WebKitLogView; +extern WTFLogChannel WebKitLogRedirect; +extern WTFLogChannel WebKitLogPageCache; +extern WTFLogChannel WebKitLogCacheSizes; +extern WTFLogChannel WebKitLogFormDelegate; +extern WTFLogChannel WebKitLogFileDatabaseActivity; +extern WTFLogChannel WebKitLogHistory; +extern WTFLogChannel WebKitLogBindings; +extern WTFLogChannel WebKitLogEncoding; +extern WTFLogChannel WebKitLogLiveConnect; +extern WTFLogChannel WebKitLogBackForward; +extern WTFLogChannel WebKitLogProgress; +extern WTFLogChannel WebKitLogPluginEvents; +extern WTFLogChannel WebKitLogIconDatabase; +extern WTFLogChannel WebKitLogTextInput; + +void WebKitInitializeLoggingChannelsIfNecessary(void); + +BOOL WebKitRunningOnMainThread(void); + +// The ASSERT_MAIN_THREAD() check should be on by default in DEBUG builds +// To disable it, even in a debug build, define DISABLE_THREAD_CHECK in your project file (or elsewhere globally) +#if !defined(NDEBUG) && !defined(DISABLE_THREAD_CHECK) +#define ASSERT_MAIN_THREAD() do \ + if (!WebKitRunningOnMainThread()) { \ + WTFReportAssertionFailure(__FILE__, __LINE__, WTF_PRETTY_FUNCTION, "<not running on main thread>"); \ + CRASH(); \ + } \ +while (0) +#else +#define ASSERT_MAIN_THREAD() ((void)0) +#endif + +void ReportDiscardedDelegateException(SEL delegateSelector, id exception); + +#ifdef __cplusplus +} +#endif diff --git a/WebKit/mac/Misc/WebKitLogging.m b/WebKit/mac/Misc/WebKitLogging.m new file mode 100644 index 0000000..4e4294f --- /dev/null +++ b/WebKit/mac/Misc/WebKitLogging.m @@ -0,0 +1,115 @@ +/* + * Copyright (C) 2005, 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebKitLogging.h" + +WTFLogChannel WebKitLogTextInput = { 0x00000010, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogTiming = { 0x00000020, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogLoading = { 0x00000040, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogFontCache = { 0x00000100, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogFontSubstitution = { 0x00000200, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogDownload = { 0x00000800, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogDocumentLoad = { 0x00001000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogPlugins = { 0x00002000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogEvents = { 0x00010000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogView = { 0x00020000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogRedirect = { 0x00040000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogPageCache = { 0x00080000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogCacheSizes = { 0x00100000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogFormDelegate = { 0x00200000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogFileDatabaseActivity = { 0x00400000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogHistory = { 0x00800000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogBindings = { 0x01000000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogFontSelection = { 0x02000000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogEncoding = { 0x04000000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogLiveConnect = { 0x08000000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogBackForward = { 0x10000000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogProgress = { 0x20000000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogPluginEvents = { 0x40000000, "WebKitLogLevel", WTFLogChannelOff }; +WTFLogChannel WebKitLogIconDatabase = { 0x80000000, "WebKitLogLevel", WTFLogChannelOff }; + +static void initializeLogChannel(WTFLogChannel *channel) +{ + channel->state = WTFLogChannelOff; + NSString *logLevelString = [[NSUserDefaults standardUserDefaults] objectForKey:[NSString stringWithUTF8String:channel->defaultName]]; + if (logLevelString) { + unsigned logLevel; + if (![[NSScanner scannerWithString:logLevelString] scanHexInt:&logLevel]) + NSLog(@"unable to parse hex value for %s (%@), logging is off", channel->defaultName, logLevelString); + if ((logLevel & channel->mask) == channel->mask) + channel->state = WTFLogChannelOn; + } +} + +void WebKitInitializeLoggingChannelsIfNecessary() +{ + static bool haveInitializedLoggingChannels = false; + if (haveInitializedLoggingChannels) + return; + haveInitializedLoggingChannels = true; + + initializeLogChannel(&WebKitLogTiming); + initializeLogChannel(&WebKitLogLoading); + initializeLogChannel(&WebKitLogFontCache); + initializeLogChannel(&WebKitLogFontSubstitution); + initializeLogChannel(&WebKitLogDownload); + initializeLogChannel(&WebKitLogDocumentLoad); + initializeLogChannel(&WebKitLogPlugins); + initializeLogChannel(&WebKitLogEvents); + initializeLogChannel(&WebKitLogView); + initializeLogChannel(&WebKitLogRedirect); + initializeLogChannel(&WebKitLogPageCache); + initializeLogChannel(&WebKitLogCacheSizes); + initializeLogChannel(&WebKitLogFormDelegate); + initializeLogChannel(&WebKitLogFileDatabaseActivity); + initializeLogChannel(&WebKitLogHistory); + initializeLogChannel(&WebKitLogBindings); + initializeLogChannel(&WebKitLogFontSelection); + initializeLogChannel(&WebKitLogEncoding); + initializeLogChannel(&WebKitLogLiveConnect); + initializeLogChannel(&WebKitLogBackForward); + initializeLogChannel(&WebKitLogProgress); + initializeLogChannel(&WebKitLogPluginEvents); + initializeLogChannel(&WebKitLogIconDatabase); + initializeLogChannel(&WebKitLogTextInput); +} + +BOOL WebKitRunningOnMainThread() +{ + return pthread_main_np() != 0; +} + +void ReportDiscardedDelegateException(SEL delegateSelector, id exception) +{ + if ([exception isKindOfClass:[NSException class]]) + NSLog(@"*** WebKit discarded an uncaught exception in the %s delegate: <%@> %@", + sel_getName(delegateSelector), [exception name], [exception reason]); + else + NSLog(@"*** WebKit discarded an uncaught exception in the %s delegate: %@", + sel_getName(delegateSelector), exception); +} diff --git a/WebKit/mac/Misc/WebKitNSStringExtras.h b/WebKit/mac/Misc/WebKitNSStringExtras.h new file mode 100644 index 0000000..47056c6 --- /dev/null +++ b/WebKit/mac/Misc/WebKitNSStringExtras.h @@ -0,0 +1,59 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + +@interface NSString (WebKitExtras) + +- (void)_web_drawAtPoint:(NSPoint)point font:(NSFont *)font textColor:(NSColor *)textColor; +- (void)_web_drawDoubledAtPoint:(NSPoint)textPoint withTopColor:(NSColor *)topColor bottomColor:(NSColor *)bottomColor font:(NSFont *)font; + +- (float)_web_widthWithFont:(NSFont *)font; + +// Handles home directories that have symlinks in their paths. +// This works around 2774250. +- (NSString *)_web_stringByAbbreviatingWithTildeInPath; + +- (NSString *)_web_stringByStrippingReturnCharacters; + ++ (NSStringEncoding)_web_encodingForResource:(Handle)resource; + +- (BOOL)_webkit_isCaseInsensitiveEqualToString:(NSString *)string; +- (BOOL)_webkit_hasCaseInsensitivePrefix:(NSString *)suffix; +- (BOOL)_webkit_hasCaseInsensitiveSuffix:(NSString *)suffix; +- (BOOL)_webkit_hasCaseInsensitiveSubstring:(NSString *)substring; +- (NSString *)_webkit_filenameByFixingIllegalCharacters; + +- (NSString *)_webkit_stringByTrimmingWhitespace; +- (NSString *)_webkit_stringByCollapsingNonPrintingCharacters; +- (NSString *)_webkit_stringByCollapsingWhitespaceCharacters; +- (NSString *)_webkit_fixedCarbonPOSIXPath; + ++ (NSString *)_webkit_localCacheDirectoryWithBundleIdentifier:(NSString*)bundleIdentifier; + +@end diff --git a/WebKit/mac/Misc/WebKitNSStringExtras.m b/WebKit/mac/Misc/WebKitNSStringExtras.m new file mode 100644 index 0000000..157069a --- /dev/null +++ b/WebKit/mac/Misc/WebKitNSStringExtras.m @@ -0,0 +1,360 @@ +/* + * Copyright (C) 2005, 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebKitNSStringExtras.h" + +#import <WebKit/WebNSObjectExtras.h> +#import <WebKit/WebNSFileManagerExtras.h> + +#import <WebCore/WebCoreNSStringExtras.h> +#import <WebCore/WebCoreTextRenderer.h> + +#import <unicode/uchar.h> +#import <sys/param.h> + +@implementation NSString (WebKitExtras) + +static BOOL canUseFastRenderer(const UniChar *buffer, unsigned length) +{ + unsigned i; + for (i = 0; i < length; i++) { + UCharDirection direction = u_charDirection(buffer[i]); + if (direction == U_RIGHT_TO_LEFT || direction > U_OTHER_NEUTRAL) + return NO; + } + return YES; +} + +- (void)_web_drawAtPoint:(NSPoint)point font:(NSFont *)font textColor:(NSColor *)textColor; +{ + // FIXME: Would be more efficient to change this to C++ and use Vector<UChar, 2048>. + unsigned length = [self length]; + UniChar *buffer = malloc(sizeof(UniChar) * length); + + [self getCharacters:buffer]; + + if (canUseFastRenderer(buffer, length)) { + // The following is a half-assed attempt to match AppKit's rounding rules for drawAtPoint. + // It's probably incorrect for high DPI. + // If you change this, be sure to test all the text drawn this way in Safari, including + // the status bar, bookmarks bar, tab bar, and activity window. + point.y = ceilf(point.y); + WebCoreDrawTextAtPoint(buffer, length, point, font, textColor); + } else { + // WebTextRenderer assumes drawing from baseline. + if ([[NSView focusView] isFlipped]) + point.y -= [font ascender]; + else { + point.y += [font descender]; + } + [self drawAtPoint:point withAttributes:[NSDictionary dictionaryWithObjectsAndKeys:font, NSFontAttributeName, textColor, NSForegroundColorAttributeName, nil]]; + } + + free(buffer); +} + +- (void)_web_drawDoubledAtPoint:(NSPoint)textPoint + withTopColor:(NSColor *)topColor + bottomColor:(NSColor *)bottomColor + font:(NSFont *)font +{ + // turn off font smoothing so translucent text draws correctly (Radar 3118455) + [NSGraphicsContext saveGraphicsState]; + CGContextSetShouldSmoothFonts([[NSGraphicsContext currentContext] graphicsPort], false); + [self _web_drawAtPoint:textPoint + font:font + textColor:bottomColor]; + + textPoint.y += 1; + [self _web_drawAtPoint:textPoint + font:font + textColor:topColor]; + [NSGraphicsContext restoreGraphicsState]; +} + +- (float)_web_widthWithFont:(NSFont *)font +{ + unsigned length = [self length]; + float width; + UniChar *buffer = (UniChar *)malloc(sizeof(UniChar) * length); + + [self getCharacters:buffer]; + + if (canUseFastRenderer(buffer, length)) + width = WebCoreTextFloatWidth(buffer, length, font); + else + width = [self sizeWithAttributes:[NSDictionary dictionaryWithObjectsAndKeys:font, NSFontAttributeName, nil]].width; + + free(buffer); + + return width; +} + +- (NSString *)_web_stringByAbbreviatingWithTildeInPath +{ + NSString *resolvedHomeDirectory = [NSHomeDirectory() stringByResolvingSymlinksInPath]; + NSString *path; + + if ([self hasPrefix:resolvedHomeDirectory]) { + NSString *relativePath = [self substringFromIndex:[resolvedHomeDirectory length]]; + path = [NSHomeDirectory() stringByAppendingPathComponent:relativePath]; + } else { + path = self; + } + + return [path stringByAbbreviatingWithTildeInPath]; +} + +- (NSString *)_web_stringByStrippingReturnCharacters +{ + NSMutableString *newString = [[self mutableCopy] autorelease]; + [newString replaceOccurrencesOfString:@"\r" withString:@"" options:NSLiteralSearch range:NSMakeRange(0, [newString length])]; + [newString replaceOccurrencesOfString:@"\n" withString:@"" options:NSLiteralSearch range:NSMakeRange(0, [newString length])]; + return newString; +} + ++ (NSStringEncoding)_web_encodingForResource:(Handle)resource +{ + short resRef = HomeResFile(resource); + if (ResError() != noErr) { + return NSMacOSRomanStringEncoding; + } + + // Get the FSRef for the current resource file + FSRef fref; + OSStatus error = FSGetForkCBInfo(resRef, 0, NULL, NULL, NULL, &fref, NULL); + if (error != noErr) { + return NSMacOSRomanStringEncoding; + } + + CFURLRef URL = CFURLCreateFromFSRef(NULL, &fref); + if (URL == NULL) { + return NSMacOSRomanStringEncoding; + } + + NSString *path = [(NSURL *)URL path]; + CFRelease(URL); + + // Get the lproj directory name + path = [path stringByDeletingLastPathComponent]; + if (![[path pathExtension] _webkit_isCaseInsensitiveEqualToString:@"lproj"]) { + return NSMacOSRomanStringEncoding; + } + + NSString *directoryName = [[path stringByDeletingPathExtension] lastPathComponent]; + CFStringRef locale = CFLocaleCreateCanonicalLocaleIdentifierFromString(NULL, (CFStringRef)directoryName); + if (locale == NULL) { + return NSMacOSRomanStringEncoding; + } + + LangCode lang; + RegionCode region; + error = LocaleStringToLangAndRegionCodes([(NSString *)locale UTF8String], &lang, ®ion); + CFRelease(locale); + if (error != noErr) { + return NSMacOSRomanStringEncoding; + } + + TextEncoding encoding; + error = UpgradeScriptInfoToTextEncoding(kTextScriptDontCare, lang, region, NULL, &encoding); + if (error != noErr) { + return NSMacOSRomanStringEncoding; + } + + return CFStringConvertEncodingToNSStringEncoding(encoding); +} + +- (BOOL)_webkit_isCaseInsensitiveEqualToString:(NSString *)string +{ + return [self compare:string options:(NSCaseInsensitiveSearch|NSLiteralSearch)] == NSOrderedSame; +} + +-(BOOL)_webkit_hasCaseInsensitivePrefix:(NSString *)prefix +{ + return [self rangeOfString:prefix options:(NSCaseInsensitiveSearch | NSAnchoredSearch)].location != NSNotFound; +} + +-(BOOL)_webkit_hasCaseInsensitiveSuffix:(NSString *)suffix +{ + return hasCaseInsensitiveSuffix(self, suffix); +} + +-(BOOL)_webkit_hasCaseInsensitiveSubstring:(NSString *)substring +{ + return hasCaseInsensitiveSubstring(self, substring); +} + +-(NSString *)_webkit_filenameByFixingIllegalCharacters +{ + return filenameByFixingIllegalCharacters(self); +} + +-(NSString *)_webkit_stringByTrimmingWhitespace +{ + NSMutableString *trimmed = [[self mutableCopy] autorelease]; + CFStringTrimWhitespace((CFMutableStringRef)trimmed); + return trimmed; +} + +- (NSString *)_webkit_stringByCollapsingNonPrintingCharacters +{ + NSMutableString *result = [NSMutableString string]; + static NSCharacterSet *charactersToTurnIntoSpaces = nil; + static NSCharacterSet *charactersToNotTurnIntoSpaces = nil; + + if (charactersToTurnIntoSpaces == nil) { + NSMutableCharacterSet *set = [[NSMutableCharacterSet alloc] init]; + [set addCharactersInRange:NSMakeRange(0x00, 0x21)]; + [set addCharactersInRange:NSMakeRange(0x7F, 0x01)]; + charactersToTurnIntoSpaces = [set copy]; + [set release]; + charactersToNotTurnIntoSpaces = [[charactersToTurnIntoSpaces invertedSet] retain]; + } + + unsigned length = [self length]; + unsigned position = 0; + while (position != length) { + NSRange nonSpace = [self rangeOfCharacterFromSet:charactersToNotTurnIntoSpaces + options:0 range:NSMakeRange(position, length - position)]; + if (nonSpace.location == NSNotFound) { + break; + } + + NSRange space = [self rangeOfCharacterFromSet:charactersToTurnIntoSpaces + options:0 range:NSMakeRange(nonSpace.location, length - nonSpace.location)]; + if (space.location == NSNotFound) { + space.location = length; + } + + if (space.location > nonSpace.location) { + if (position != 0) { + [result appendString:@" "]; + } + [result appendString:[self substringWithRange: + NSMakeRange(nonSpace.location, space.location - nonSpace.location)]]; + } + + position = space.location; + } + + return result; +} + +- (NSString *)_webkit_stringByCollapsingWhitespaceCharacters +{ + NSMutableString *result = [[NSMutableString alloc] initWithCapacity:[self length]]; + NSCharacterSet *spaces = [NSCharacterSet whitespaceAndNewlineCharacterSet]; + static NSCharacterSet *notSpaces = nil; + + if (notSpaces == nil) + notSpaces = [[spaces invertedSet] retain]; + + unsigned length = [self length]; + unsigned position = 0; + while (position != length) { + NSRange nonSpace = [self rangeOfCharacterFromSet:notSpaces options:0 range:NSMakeRange(position, length - position)]; + if (nonSpace.location == NSNotFound) + break; + + NSRange space = [self rangeOfCharacterFromSet:spaces options:0 range:NSMakeRange(nonSpace.location, length - nonSpace.location)]; + if (space.location == NSNotFound) + space.location = length; + + if (space.location > nonSpace.location) { + if (position != 0) + [result appendString:@" "]; + [result appendString:[self substringWithRange:NSMakeRange(nonSpace.location, space.location - nonSpace.location)]]; + } + + position = space.location; + } + + return [result autorelease]; +} + +-(NSString *)_webkit_fixedCarbonPOSIXPath +{ + NSFileManager *fileManager = [NSFileManager defaultManager]; + if ([fileManager fileExistsAtPath:self]) { + // Files exists, no need to fix. + return self; + } + + NSMutableArray *pathComponents = [[[self pathComponents] mutableCopy] autorelease]; + NSString *volumeName = [pathComponents objectAtIndex:1]; + if ([volumeName isEqualToString:@"Volumes"]) { + // Path starts with "/Volumes", so the volume name is the next path component. + volumeName = [pathComponents objectAtIndex:2]; + // Remove "Volumes" from the path because it may incorrectly be part of the path (3163647). + // We'll add it back if we have to. + [pathComponents removeObjectAtIndex:1]; + } + + if (!volumeName) { + // Should only happen if self == "/", so this shouldn't happen because that always exists. + return self; + } + + if ([[fileManager _webkit_startupVolumeName] isEqualToString:volumeName]) { + // Startup volume name is included in path, remove it. + [pathComponents removeObjectAtIndex:1]; + } else if ([[fileManager contentsOfDirectoryAtPath:@"/Volumes" error:NULL] containsObject:volumeName]) { + // Path starts with other volume name, prepend "/Volumes". + [pathComponents insertObject:@"Volumes" atIndex:1]; + } else + // It's valid. + return self; + + NSString *path = [NSString pathWithComponents:pathComponents]; + + if (![fileManager fileExistsAtPath:path]) + // File at canonicalized path doesn't exist, return original. + return self; + + return path; +} + ++ (NSString *)_webkit_localCacheDirectoryWithBundleIdentifier:(NSString*)bundleIdentifier +{ + NSString* cacheDir = nil; + +#ifdef BUILDING_ON_TIGER + cacheDir = [NSHomeDirectory() stringByAppendingPathComponent:@"Library/Caches"]; +#else + char cacheDirectory[MAXPATHLEN]; + size_t cacheDirectoryLen = confstr(_CS_DARWIN_USER_CACHE_DIR, cacheDirectory, MAXPATHLEN); + + if (cacheDirectoryLen) + cacheDir = [[NSFileManager defaultManager] stringWithFileSystemRepresentation:cacheDirectory length:cacheDirectoryLen - 1]; +#endif + + return [cacheDir stringByAppendingPathComponent:bundleIdentifier]; +} + + +@end diff --git a/WebKit/mac/Misc/WebKitStatistics.h b/WebKit/mac/Misc/WebKitStatistics.h new file mode 100644 index 0000000..32241b5 --- /dev/null +++ b/WebKit/mac/Misc/WebKitStatistics.h @@ -0,0 +1,41 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@interface WebKitStatistics : NSObject + ++ (int)webViewCount; + ++ (int)frameCount; ++ (int)dataSourceCount; ++ (int)viewCount; ++ (int)HTMLRepresentationCount; ++ (int)bridgeCount; + +@end diff --git a/WebKit/mac/Misc/WebKitStatistics.m b/WebKit/mac/Misc/WebKitStatistics.m new file mode 100644 index 0000000..3e40324 --- /dev/null +++ b/WebKit/mac/Misc/WebKitStatistics.m @@ -0,0 +1,72 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebKitStatistics.h" + +#import "WebKitStatisticsPrivate.h" + +int WebViewCount; +int WebDataSourceCount; +int WebFrameCount; +int WebHTMLRepresentationCount; +int WebFrameViewCount; + +@implementation WebKitStatistics + ++ (int)webViewCount +{ + return WebViewCount; +} + ++ (int)frameCount +{ + return WebFrameCount; +} + ++ (int)dataSourceCount +{ + return WebDataSourceCount; +} + ++ (int)viewCount +{ + return WebFrameViewCount; +} + ++ (int)bridgeCount +{ + // No such thing as a bridge any more. Just return 0. + return 0; +} + ++ (int)HTMLRepresentationCount +{ + return WebHTMLRepresentationCount; +} + +@end diff --git a/WebKit/mac/Misc/WebKitStatisticsPrivate.h b/WebKit/mac/Misc/WebKitStatisticsPrivate.h new file mode 100644 index 0000000..e69bc51 --- /dev/null +++ b/WebKit/mac/Misc/WebKitStatisticsPrivate.h @@ -0,0 +1,33 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +extern int WebViewCount; +extern int WebDataSourceCount; +extern int WebFrameCount; +extern int WebHTMLRepresentationCount; +extern int WebFrameViewCount; diff --git a/WebKit/mac/Misc/WebKitSystemBits.h b/WebKit/mac/Misc/WebKitSystemBits.h new file mode 100644 index 0000000..fe627ee --- /dev/null +++ b/WebKit/mac/Misc/WebKitSystemBits.h @@ -0,0 +1,41 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +#ifdef __cplusplus +extern "C" { +#endif + +uint64_t WebMemorySize(void); +unsigned long long WebVolumeFreeSize(NSString *path); +int WebNumberOfCPUs(void); + +#ifdef __cplusplus +} +#endif diff --git a/WebKit/mac/Misc/WebKitSystemBits.m b/WebKit/mac/Misc/WebKitSystemBits.m new file mode 100644 index 0000000..d64f2de --- /dev/null +++ b/WebKit/mac/Misc/WebKitSystemBits.m @@ -0,0 +1,84 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebKitSystemBits.h" + +#import "WebNSFileManagerExtras.h" +#import <mach/host_info.h> +#import <mach/mach.h> +#import <mach/mach_error.h> +#import <sys/sysctl.h> +#import <sys/types.h> +#import <wtf/Assertions.h> + +static host_basic_info_data_t gHostBasicInfo; +static pthread_once_t initControl = PTHREAD_ONCE_INIT; + +static void initCapabilities(void) +{ + mach_msg_type_number_t count; + kern_return_t r; + mach_port_t host; + + /* Discover our CPU type */ + host = mach_host_self(); + count = HOST_BASIC_INFO_COUNT; + r = host_info(host, HOST_BASIC_INFO, (host_info_t) &gHostBasicInfo, &count); + mach_port_deallocate(mach_task_self(), host); + if (r != KERN_SUCCESS) { + LOG_ERROR("%s : host_info(%d) : %s.\n", __FUNCTION__, r, mach_error_string(r)); + } +} + +uint64_t WebMemorySize(void) +{ + pthread_once(&initControl, initCapabilities); + return gHostBasicInfo.max_mem; +} + +int WebNumberOfCPUs(void) +{ + static int numCPUs = 0; + + if (numCPUs == 0) { + int mib[2]; + size_t len; + + mib[0] = CTL_HW; + mib[1] = HW_NCPU; + len = sizeof(numCPUs); + sysctl(mib, 2, &numCPUs, &len, NULL, 0); + } + return numCPUs; +} + +unsigned long long WebVolumeFreeSize(NSString *path) +{ + NSDictionary *fileSystemAttributesDictionary = [[NSFileManager defaultManager] attributesOfFileSystemForPath:path error:NULL]; + return [[fileSystemAttributesDictionary objectForKey:NSFileSystemFreeSize] unsignedLongLongValue]; +} diff --git a/WebKit/mac/Misc/WebKitVersionChecks.h b/WebKit/mac/Misc/WebKitVersionChecks.h new file mode 100644 index 0000000..33dc38b --- /dev/null +++ b/WebKit/mac/Misc/WebKitVersionChecks.h @@ -0,0 +1,62 @@ +/* + * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/* + Version numbers are based on the 'current library version' specified in the WebKit build rules. + All of these methods return or take version numbers with each part shifted to the left 2 bytes. + For example the version 1.2.3 is returned as 0x00010203 and version 200.3.5 is returned as 0x00C80305 + A version of -1 is returned if the main executable did not link against WebKit (should never happen). + + Please use the current WebKit version number, available in WebKit/Configurations/Version.xcconfig, + when adding a new version constant. +*/ + +#define WEBKIT_FIRST_VERSION_WITH_3_0_CONTEXT_MENU_TAGS 0x020A0000 // 522.0.0 +#define WEBKIT_FIRST_VERSION_WITH_LOCAL_RESOURCE_SECURITY_RESTRICTION 0x020A0000 // 522.0.0 +#define WEBKIT_FIRST_VERSION_WITHOUT_APERTURE_QUIRK 0x020A0000 // 522.0.0 +#define WEBKIT_FIRST_VERSION_WITHOUT_QUICKBOOKS_QUIRK 0x020A0000 // 522.0.0 +#define WEBKIT_FIRST_VERSION_WITH_MAIN_THREAD_EXCEPTIONS 0x020A0000 // 522.0.0 +#define WEBKIT_FIRST_VERSION_WITHOUT_ADOBE_INSTALLER_QUIRK 0x020A0000 // 522.0.0 +#define WEBKIT_FIRST_VERSION_WITH_INSPECT_ELEMENT_MENU_TAG 0x020A0C00 // 522.12.0 +#define WEBKIT_FIRST_VERSION_WITH_CACHE_MODEL_API 0x020B0500 // 523.5.0 +#define WEBKIT_FIRST_VERSION_WITHOUT_JAVASCRIPT_RETURN_QUIRK 0x020D0100 // 525.1.0 +#define WEBKIT_FIRST_VERSION_WITH_IE_COMPATIBLE_KEYBOARD_EVENT_DISPATCH 0x020D0100 // 525.1.0 +#define WEBKIT_FIRST_VERSION_WITH_LOADING_DURING_COMMON_RUNLOOP_MODES 0x020E0000 // 526.0.0 +#define WEBKIT_FIRST_VERSION_WITH_MORE_STRICT_LOCAL_RESOURCE_SECURITY_RESTRICTION 0x02100200 // 528.2.0 + +#ifdef __cplusplus +extern "C" { +#endif + +BOOL WebKitLinkedOnOrAfter(int version); +int WebKitLinkTimeVersion(void); +int WebKitRunTimeVersion(void); + +#ifdef __cplusplus +} +#endif diff --git a/WebKit/mac/Misc/WebKitVersionChecks.m b/WebKit/mac/Misc/WebKitVersionChecks.m new file mode 100644 index 0000000..5659273 --- /dev/null +++ b/WebKit/mac/Misc/WebKitVersionChecks.m @@ -0,0 +1,45 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebKitVersionChecks.h" +#import <mach-o/dyld.h> + +BOOL WebKitLinkedOnOrAfter(int version) +{ + return (WebKitLinkTimeVersion() >= version); +} + +int WebKitLinkTimeVersion(void) +{ + return NSVersionOfLinkTimeLibrary("WebKit"); +} + +int WebKitRunTimeVersion(void) +{ + return NSVersionOfRunTimeLibrary("WebKit"); +} diff --git a/WebKit/mac/Misc/WebLocalizableStrings.h b/WebKit/mac/Misc/WebLocalizableStrings.h new file mode 100644 index 0000000..ecad83d --- /dev/null +++ b/WebKit/mac/Misc/WebLocalizableStrings.h @@ -0,0 +1,68 @@ +/* + * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#if __OBJC__ +@class NSBundle; +#else +typedef struct NSBundle NSBundle; +#endif + +typedef struct { + const char *identifier; + NSBundle *bundle; +} WebLocalizableStringsBundle; + +#ifdef __cplusplus +extern "C" { +#endif + +#if __OBJC__ +NSString *WebLocalizedString(WebLocalizableStringsBundle *bundle, const char *key); +#else +CFStringRef WebLocalizedString(WebLocalizableStringsBundle *bundle, const char *key); +#endif + +#ifdef __cplusplus +} +#endif + +#ifdef FRAMEWORK_NAME + +#define LOCALIZABLE_STRINGS_BUNDLE(F) LOCALIZABLE_STRINGS_BUNDLE_HELPER(F) +#define LOCALIZABLE_STRINGS_BUNDLE_HELPER(F) F ## LocalizableStringsBundle +extern WebLocalizableStringsBundle LOCALIZABLE_STRINGS_BUNDLE(FRAMEWORK_NAME); + +#define UI_STRING(string, comment) WebLocalizedString(&LOCALIZABLE_STRINGS_BUNDLE(FRAMEWORK_NAME), string) +#define UI_STRING_KEY(string, key, comment) WebLocalizedString(&LOCALIZABLE_STRINGS_BUNDLE(FRAMEWORK_NAME), key) + +#else + +#define UI_STRING(string, comment) WebLocalizedString(0, string) +#define UI_STRING_KEY(string, key, comment) WebLocalizedString(0, key) + +#endif diff --git a/WebKit/mac/Misc/WebLocalizableStrings.m b/WebKit/mac/Misc/WebLocalizableStrings.m new file mode 100644 index 0000000..0babfbc --- /dev/null +++ b/WebKit/mac/Misc/WebLocalizableStrings.m @@ -0,0 +1,60 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebLocalizableStrings.h> + +#import <wtf/Assertions.h> + +WebLocalizableStringsBundle WebKitLocalizableStringsBundle = { "com.apple.WebKit", 0 }; + +NSString *WebLocalizedString(WebLocalizableStringsBundle *stringsBundle, const char *key) +{ + NSBundle *bundle; + if (stringsBundle == NULL) { + static NSBundle *mainBundle; + if (mainBundle == nil) { + mainBundle = [NSBundle mainBundle]; + ASSERT(mainBundle); + CFRetain(mainBundle); + } + bundle = mainBundle; + } else { + bundle = stringsBundle->bundle; + if (bundle == nil) { + bundle = [NSBundle bundleWithIdentifier:[NSString stringWithUTF8String:stringsBundle->identifier]]; + ASSERT(bundle); + stringsBundle->bundle = bundle; + } + } + NSString *notFound = @"localized string not found"; + CFStringRef keyString = CFStringCreateWithCStringNoCopy(NULL, key, kCFStringEncodingUTF8, kCFAllocatorNull); + NSString *result = [bundle localizedStringForKey:(NSString *)keyString value:notFound table:nil]; + CFRelease(keyString); + ASSERT_WITH_MESSAGE(result != notFound, "could not find localizable string %s in bundle", key); + return result; +} diff --git a/WebKit/mac/Misc/WebNSArrayExtras.h b/WebKit/mac/Misc/WebNSArrayExtras.h new file mode 100644 index 0000000..5e3294d --- /dev/null +++ b/WebKit/mac/Misc/WebNSArrayExtras.h @@ -0,0 +1,36 @@ +/* + * Copyright (C) 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + + +@interface NSMutableArray (WebNSArrayExtras) + +- (void)_webkit_removeUselessMenuItemSeparators; + +@end diff --git a/WebKit/mac/Misc/WebNSArrayExtras.m b/WebKit/mac/Misc/WebNSArrayExtras.m new file mode 100644 index 0000000..b8b9af3 --- /dev/null +++ b/WebKit/mac/Misc/WebNSArrayExtras.m @@ -0,0 +1,58 @@ +/* + * Copyright (C) 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSArrayExtras.h" + +#import <wtf/Assertions.h> + +@implementation NSMutableArray (WebExtras) + +- (void)_webkit_removeUselessMenuItemSeparators +{ + // Starting with a mutable array of NSMenuItems, removes any separators at the start, + // removes any separators at the end, and collapses any other adjacent separators to + // a single separator. + + int index; + // Start this with YES so very last item will be removed if it's a separator. + BOOL removePreviousItemIfSeparator = YES; + for (index = [self count] - 1; index >= 0; --index) { + NSMenuItem *item = [self objectAtIndex:index]; + ASSERT([item isKindOfClass:[NSMenuItem class]]); + BOOL itemIsSeparator = [item isSeparatorItem]; + if (itemIsSeparator && (removePreviousItemIfSeparator || index == 0)) + [self removeObjectAtIndex:index]; + removePreviousItemIfSeparator = itemIsSeparator; + } + + // This could leave us with one initial separator; kill it off too + if ([self count] && [[self objectAtIndex:0] isSeparatorItem]) + [self removeObjectAtIndex:0]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSAttributedStringExtras.h b/WebKit/mac/Misc/WebNSAttributedStringExtras.h new file mode 100644 index 0000000..a4ee9fc --- /dev/null +++ b/WebKit/mac/Misc/WebNSAttributedStringExtras.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +namespace WebCore { + class Range; +} + +@interface NSAttributedString (WebKitExtras) + ++ (NSAttributedString *)_web_attributedStringFromRange:(WebCore::Range*)range; +- (NSAttributedString *)_web_attributedStringByStrippingAttachmentCharacters; + +@end diff --git a/WebKit/mac/Misc/WebNSAttributedStringExtras.mm b/WebKit/mac/Misc/WebNSAttributedStringExtras.mm new file mode 100644 index 0000000..ef472aa --- /dev/null +++ b/WebKit/mac/Misc/WebNSAttributedStringExtras.mm @@ -0,0 +1,175 @@ +/* + * Copyright (C) 2005, 2007, 2008 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSAttributedStringExtras.h" + +#import "DOMRangeInternal.h" +#import "WebDataSourcePrivate.h" +#import "WebFrame.h" +#import "WebFrameInternal.h" +#import "WebTypesInternal.h" +#import <WebCore/BlockExceptions.h> +#import <WebCore/ColorMac.h> +#import <WebCore/CSSHelper.h> +#import <WebCore/Document.h> +#import <WebCore/Element.h> +#import <WebCore/Frame.h> +#import <WebCore/FrameLoader.h> +#import <WebCore/HTMLNames.h> +#import <WebCore/Image.h> +#import <WebCore/InlineTextBox.h> +#import <WebCore/Range.h> +#import <WebCore/RenderImage.h> +#import <WebCore/RenderListItem.h> +#import <WebCore/RenderObject.h> +#import <WebCore/RenderStyle.h> +#import <WebCore/RenderText.h> +#import <WebCore/SimpleFontData.h> +#import <WebCore/Text.h> +#import <WebCore/TextIterator.h> + +using namespace WebCore; +using namespace HTMLNames; + +struct ListItemInfo { + unsigned start; + unsigned end; +}; + +static NSFileWrapper *fileWrapperForElement(Element* e) +{ + NSFileWrapper *wrapper = nil; + BEGIN_BLOCK_OBJC_EXCEPTIONS; + + const AtomicString& attr = e->getAttribute(srcAttr); + if (!attr.isEmpty()) { + NSURL *URL = e->document()->completeURL(attr); + wrapper = [[kit(e->document()->frame()) _dataSource] _fileWrapperForURL:URL]; + } + if (!wrapper) { + RenderImage* renderer = static_cast<RenderImage*>(e->renderer()); + if (renderer->cachedImage() && !renderer->cachedImage()->errorOccurred()) { + wrapper = [[NSFileWrapper alloc] initRegularFileWithContents:(NSData *)(renderer->cachedImage()->image()->getTIFFRepresentation())]; + [wrapper setPreferredFilename:@"image.tiff"]; + [wrapper autorelease]; + } + } + + return wrapper; + + END_BLOCK_OBJC_EXCEPTIONS; + + return nil; +} + +@implementation NSAttributedString (WebKitExtras) + +- (NSAttributedString *)_web_attributedStringByStrippingAttachmentCharacters +{ + // This code was originally copied from NSTextView + NSRange attachmentRange; + NSString *originalString = [self string]; + static NSString *attachmentCharString = nil; + + if (!attachmentCharString) { + unichar chars[2]; + if (!attachmentCharString) { + chars[0] = NSAttachmentCharacter; + chars[1] = 0; + attachmentCharString = [[NSString alloc] initWithCharacters:chars length:1]; + } + } + + attachmentRange = [originalString rangeOfString:attachmentCharString]; + if (attachmentRange.location != NSNotFound && attachmentRange.length > 0) { + NSMutableAttributedString *newAttributedString = [[self mutableCopyWithZone:NULL] autorelease]; + + while (attachmentRange.location != NSNotFound && attachmentRange.length > 0) { + [newAttributedString replaceCharactersInRange:attachmentRange withString:@""]; + attachmentRange = [[newAttributedString string] rangeOfString:attachmentCharString]; + } + return newAttributedString; + } + + return self; +} + ++ (NSAttributedString *)_web_attributedStringFromRange:(Range*)range +{ + NSMutableAttributedString *string = [[NSMutableAttributedString alloc] init]; + NSUInteger stringLength = 0; + RetainPtr<NSMutableDictionary> attrs(AdoptNS, [[NSMutableDictionary alloc] init]); + + for (TextIterator it(range); !it.atEnd(); it.advance()) { + RefPtr<Range> currentTextRange = it.range(); + ExceptionCode ec = 0; + Node* startContainer = currentTextRange->startContainer(ec); + Node* endContainer = currentTextRange->endContainer(ec); + int startOffset = currentTextRange->startOffset(ec); + int endOffset = currentTextRange->endOffset(ec); + + if (startContainer == endContainer && (startOffset == endOffset - 1)) { + Node* node = startContainer->childNode(startOffset); + if (node && node->hasTagName(imgTag)) { + NSFileWrapper *fileWrapper = fileWrapperForElement(static_cast<Element*>(node)); + NSTextAttachment *attachment = [[NSTextAttachment alloc] initWithFileWrapper:fileWrapper]; + [string appendAttributedString:[NSAttributedString attributedStringWithAttachment:attachment]]; + [attachment release]; + } + } + + int currentTextLength = it.length(); + if (!currentTextLength) + continue; + + RenderObject* renderer = startContainer->renderer(); + ASSERT(renderer); + if (!renderer) + continue; + RenderStyle* style = renderer->style(); + NSFont *font = style->font().primaryFont()->getNSFont(); + [attrs.get() setObject:font forKey:NSFontAttributeName]; + if (style->color().isValid()) + [attrs.get() setObject:nsColor(style->color()) forKey:NSForegroundColorAttributeName]; + else + [attrs.get() removeObjectForKey:NSForegroundColorAttributeName]; + if (style->backgroundColor().isValid()) + [attrs.get() setObject:nsColor(style->backgroundColor()) forKey:NSBackgroundColorAttributeName]; + else + [attrs.get() removeObjectForKey:NSBackgroundColorAttributeName]; + + RetainPtr<NSString> substring(AdoptNS, [[NSString alloc] initWithCharactersNoCopy:const_cast<UChar*>(it.characters()) length:currentTextLength freeWhenDone:NO]); + [string replaceCharactersInRange:NSMakeRange(stringLength, 0) withString:substring.get()]; + [string setAttributes:attrs.get() range:NSMakeRange(stringLength, currentTextLength)]; + stringLength += currentTextLength; + } + + return [string autorelease]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSControlExtras.h b/WebKit/mac/Misc/WebNSControlExtras.h new file mode 100644 index 0000000..cf4cfa6 --- /dev/null +++ b/WebKit/mac/Misc/WebNSControlExtras.h @@ -0,0 +1,33 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + +@interface NSControl (WebExtras) +- (void)sizeToFitAndAdjustWindowHeight; +@end diff --git a/WebKit/mac/Misc/WebNSControlExtras.m b/WebKit/mac/Misc/WebNSControlExtras.m new file mode 100644 index 0000000..b666131 --- /dev/null +++ b/WebKit/mac/Misc/WebNSControlExtras.m @@ -0,0 +1,51 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSControlExtras.h" + +@implementation NSControl (WebExtras) + +- (void)sizeToFitAndAdjustWindowHeight +{ + NSRect frame = [self frame]; + + NSSize bestSize = [[self cell] cellSizeForBounds:NSMakeRect(0.0f, 0.0f, frame.size.width, 10000.0f)]; + + float heightDelta = bestSize.height - frame.size.height; + + frame.size.height += heightDelta; + frame.origin.y -= heightDelta; + [self setFrame:frame]; + + NSWindow *window = [self window]; + NSRect windowFrame = [window frame]; + windowFrame.size.height += heightDelta * [window userSpaceScaleFactor]; + [window setFrame:windowFrame display:NO]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSDataExtras.h b/WebKit/mac/Misc/WebNSDataExtras.h new file mode 100644 index 0000000..d6ce829 --- /dev/null +++ b/WebKit/mac/Misc/WebNSDataExtras.h @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +#define WEB_GUESS_MIME_TYPE_PEEK_LENGTH 1024 + +@interface NSData (WebNSDataExtras) + +-(BOOL)_web_isCaseInsensitiveEqualToCString:(const char *)string; +-(NSMutableDictionary *)_webkit_parseRFC822HeaderFields; + +@end diff --git a/WebKit/mac/Misc/WebNSDataExtras.m b/WebKit/mac/Misc/WebNSDataExtras.m new file mode 100644 index 0000000..0bd4555 --- /dev/null +++ b/WebKit/mac/Misc/WebNSDataExtras.m @@ -0,0 +1,395 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebNSDataExtras.h> +#import <WebKit/WebNSDataExtrasPrivate.h> + +#import <wtf/Assertions.h> + +@interface NSString (WebNSDataExtrasInternal) +- (NSString *)_web_capitalizeRFC822HeaderFieldName; +@end + +@implementation NSString (WebNSDataExtrasInternal) + +-(NSString *)_web_capitalizeRFC822HeaderFieldName +{ + CFStringRef name = (CFStringRef)self; + NSString *result = nil; + + CFIndex i; + CFIndex len = CFStringGetLength(name); + char *charPtr = NULL; + UniChar *uniCharPtr = NULL; + Boolean useUniCharPtr = FALSE; + Boolean shouldCapitalize = TRUE; + Boolean somethingChanged = FALSE; + + for (i = 0; i < len; i ++) { + UniChar ch = CFStringGetCharacterAtIndex(name, i); + Boolean replace = FALSE; + if (shouldCapitalize && ch >= 'a' && ch <= 'z') { + ch = ch + 'A' - 'a'; + replace = TRUE; + } + else if (!shouldCapitalize && ch >= 'A' && ch <= 'Z') { + ch = ch + 'a' - 'A'; + replace = TRUE; + } + if (replace) { + if (!somethingChanged) { + somethingChanged = TRUE; + if (CFStringGetBytes(name, CFRangeMake(0, len), kCFStringEncodingISOLatin1, 0, FALSE, NULL, 0, NULL) == len) { + // Can be encoded in ISOLatin1 + useUniCharPtr = FALSE; + charPtr = CFAllocatorAllocate(NULL, len + 1, 0); + CFStringGetCString(name, charPtr, len+1, kCFStringEncodingISOLatin1); + } + else { + useUniCharPtr = TRUE; + uniCharPtr = CFAllocatorAllocate(NULL, len * sizeof(UniChar), 0); + CFStringGetCharacters(name, CFRangeMake(0, len), uniCharPtr); + } + } + if (useUniCharPtr) { + uniCharPtr[i] = ch; + } + else { + charPtr[i] = ch; + } + } + if (ch == '-') { + shouldCapitalize = TRUE; + } + else { + shouldCapitalize = FALSE; + } + } + if (somethingChanged) { + if (useUniCharPtr) { + result = (NSString *)CFMakeCollectable(CFStringCreateWithCharactersNoCopy(NULL, uniCharPtr, len, NULL)); + } + else { + result = (NSString *)CFMakeCollectable(CFStringCreateWithCStringNoCopy(NULL, charPtr, kCFStringEncodingISOLatin1, NULL)); + } + } + else { + result = [self retain]; + } + + return [result autorelease]; +} + +@end + +@implementation NSData (WebKitExtras) + +-(NSString *)_webkit_guessedMIMETypeForXML +{ + int length = [self length]; + const UInt8 *bytes = [self bytes]; + +#define CHANNEL_TAG_LENGTH 7 + + const char *p = (const char *)bytes; + int remaining = MIN(length, WEB_GUESS_MIME_TYPE_PEEK_LENGTH) - (CHANNEL_TAG_LENGTH - 1); + + BOOL foundRDF = false; + + while (remaining > 0) { + // Look for a "<". + const char *hit = memchr(p, '<', remaining); + if (!hit) { + break; + } + + // We are trying to identify RSS or Atom. RSS has a top-level + // element of either <rss> or <rdf>. However, there are + // non-RSS RDF files, so in the case of <rdf> we further look + // for a <channel> element. In the case of an Atom file, a + // top-level <feed> element is all we need to see. Only tags + // starting with <? or <! can precede the root element. We + // bail if we don't find an <rss>, <feed> or <rdf> element + // right after those. + + if (foundRDF) { + if (strncasecmp(hit, "<channel", strlen("<channel")) == 0) { + return @"application/rss+xml"; + } + } else if (strncasecmp(hit, "<rdf", strlen("<rdf")) == 0) { + foundRDF = TRUE; + } else if (strncasecmp(hit, "<rss", strlen("<rss")) == 0) { + return @"application/rss+xml"; + } else if (strncasecmp(hit, "<feed", strlen("<feed")) == 0) { + return @"application/atom+xml"; + } else if (strncasecmp(hit, "<?", strlen("<?")) != 0 && strncasecmp(hit, "<!", strlen("<!")) != 0) { + return nil; + } + + // Skip the "<" and continue. + remaining -= (hit + 1) - p; + p = hit + 1; + } + + return nil; +} + +-(NSString *)_webkit_guessedMIMEType +{ +#define JPEG_MAGIC_NUMBER_LENGTH 4 +#define SCRIPT_TAG_LENGTH 7 +#define TEXT_HTML_LENGTH 9 +#define VCARD_HEADER_LENGTH 11 +#define VCAL_HEADER_LENGTH 15 + + NSString *MIMEType = [self _webkit_guessedMIMETypeForXML]; + if ([MIMEType length]) + return MIMEType; + + int length = [self length]; + const char *bytes = [self bytes]; + + const char *p = bytes; + int remaining = MIN(length, WEB_GUESS_MIME_TYPE_PEEK_LENGTH) - (SCRIPT_TAG_LENGTH - 1); + while (remaining > 0) { + // Look for a "<". + const char *hit = memchr(p, '<', remaining); + if (!hit) { + break; + } + + // If we found a "<", look for "<html>" or "<a " or "<script". + if (strncasecmp(hit, "<html>", strlen("<html>")) == 0 || + strncasecmp(hit, "<a ", strlen("<a ")) == 0 || + strncasecmp(hit, "<script", strlen("<script")) == 0 || + strncasecmp(hit, "<title>", strlen("<title>")) == 0) { + return @"text/html"; + } + + // Skip the "<" and continue. + remaining -= (hit + 1) - p; + p = hit + 1; + } + + // Test for a broken server which has sent the content type as part of the content. + // This code could be improved to look for other mime types. + p = bytes; + remaining = MIN(length, WEB_GUESS_MIME_TYPE_PEEK_LENGTH) - (TEXT_HTML_LENGTH - 1); + while (remaining > 0) { + // Look for a "t" or "T". + const char *hit = NULL; + const char *lowerhit = memchr(p, 't', remaining); + const char *upperhit = memchr(p, 'T', remaining); + if (!lowerhit && !upperhit) { + break; + } + if (!lowerhit) { + hit = upperhit; + } + else if (!upperhit) { + hit = lowerhit; + } + else { + hit = MIN(lowerhit, upperhit); + } + + // If we found a "t/T", look for "text/html". + if (strncasecmp(hit, "text/html", TEXT_HTML_LENGTH) == 0) { + return @"text/html"; + } + + // Skip the "t/T" and continue. + remaining -= (hit + 1) - p; + p = hit + 1; + } + + if ((length >= VCARD_HEADER_LENGTH) && strncmp(bytes, "BEGIN:VCARD", VCARD_HEADER_LENGTH) == 0) { + return @"text/vcard"; + } + if ((length >= VCAL_HEADER_LENGTH) && strncmp(bytes, "BEGIN:VCALENDAR", VCAL_HEADER_LENGTH) == 0) { + return @"text/calendar"; + } + + // Test for plain text. + int i; + for(i=0; i<length; i++){ + char c = bytes[i]; + if ((c < 0x20 || c > 0x7E) && (c != '\t' && c != '\r' && c != '\n')) { + break; + } + } + if (i == length) { + // Didn't encounter any bad characters, looks like plain text. + return @"text/plain"; + } + + // Looks like this is a binary file. + + // Sniff for the JPEG magic number. + if ((length >= JPEG_MAGIC_NUMBER_LENGTH) && strncmp(bytes, "\xFF\xD8\xFF\xE0", JPEG_MAGIC_NUMBER_LENGTH) == 0) { + return @"image/jpeg"; + } + +#undef JPEG_MAGIC_NUMBER_LENGTH +#undef SCRIPT_TAG_LENGTH +#undef TEXT_HTML_LENGTH +#undef VCARD_HEADER_LENGTH +#undef VCAL_HEADER_LENGTH + + return nil; +} + +@end + +@implementation NSData (WebNSDataExtras) + +-(BOOL)_web_isCaseInsensitiveEqualToCString:(const char *)string +{ + ASSERT(string); + + const char *bytes = [self bytes]; + return strncasecmp(bytes, string, [self length]) == 0; +} + +static const UInt8 *_findEOL(const UInt8 *bytes, CFIndex len) { + + // According to the HTTP specification EOL is defined as + // a CRLF pair. Unfortunately, some servers will use LF + // instead. Worse yet, some servers will use a combination + // of both (e.g. <header>CRLFLF<body>), so findEOL needs + // to be more forgiving. It will now accept CRLF, LF, or + // CR. + // + // It returns NULL if EOL is not found or it will return + // a pointer to the first terminating character. + CFIndex i; + for (i = 0; i < len; i++) + { + UInt8 c = bytes[i]; + if ('\n' == c) return bytes + i; + if ('\r' == c) + { + // Check to see if spanning buffer bounds + // (CRLF is across reads). If so, wait for + // next read. + if (i + 1 == len) break; + + return bytes + i; + } + } + + return NULL; +} + +-(NSMutableDictionary *)_webkit_parseRFC822HeaderFields +{ + NSMutableDictionary *headerFields = [NSMutableDictionary dictionary]; + + const UInt8 *bytes = [self bytes]; + unsigned length = [self length]; + NSString *lastKey = nil; + const UInt8 *eol; + + // Loop over lines until we're past the header, or we can't find any more end-of-lines + while ((eol = _findEOL(bytes, length))) { + const UInt8 *line = bytes; + SInt32 lineLength = eol - bytes; + + // Move bytes to the character after the terminator as returned by _findEOL. + bytes = eol + 1; + if (('\r' == *eol) && ('\n' == *bytes)) { + bytes++; // Safe since _findEOL won't return a spanning CRLF. + } + + length -= (bytes - line); + if (lineLength == 0) { + // Blank line; we're at the end of the header + break; + } + else if (*line == ' ' || *line == '\t') { + // Continuation of the previous header + if (!lastKey) { + // malformed header; ignore it and continue + continue; + } + else { + // Merge the continuation of the previous header + NSString *currentValue = [headerFields objectForKey:lastKey]; + NSString *newValue = (NSString *)CFMakeCollectable(CFStringCreateWithBytes(NULL, line, lineLength, kCFStringEncodingISOLatin1, FALSE)); + ASSERT(currentValue); + ASSERT(newValue); + NSString *mergedValue = [[NSString alloc] initWithFormat:@"%@%@", currentValue, newValue]; + [headerFields setObject:(NSString *)mergedValue forKey:lastKey]; + [newValue release]; + [mergedValue release]; + // Note: currentValue is autoreleased + } + } + else { + // Brand new header + const UInt8 *colon; + for (colon = line; *colon != ':' && colon != eol; colon ++) { + // empty loop + } + if (colon == eol) { + // malformed header; ignore it and continue + continue; + } + else { + lastKey = (NSString *)CFMakeCollectable(CFStringCreateWithBytes(NULL, line, colon - line, kCFStringEncodingISOLatin1, FALSE)); + [lastKey autorelease]; + NSString *value = [lastKey _web_capitalizeRFC822HeaderFieldName]; + lastKey = value; + for (colon++; colon != eol; colon++) { + if (*colon != ' ' && *colon != '\t') { + break; + } + } + if (colon == eol) { + value = [[NSString alloc] initWithString:@""]; + [value autorelease]; + } + else { + value = (NSString *)CFMakeCollectable(CFStringCreateWithBytes(NULL, colon, eol-colon, kCFStringEncodingISOLatin1, FALSE)); + [value autorelease]; + } + NSString *oldValue = [headerFields objectForKey:lastKey]; + if (oldValue) { + NSString *newValue = [[NSString alloc] initWithFormat:@"%@, %@", oldValue, value]; + value = newValue; + [newValue autorelease]; + } + [headerFields setObject:(NSString *)value forKey:lastKey]; + } + } + } + + return headerFields; +} + +@end diff --git a/WebKit/mac/Misc/WebNSDataExtrasPrivate.h b/WebKit/mac/Misc/WebNSDataExtrasPrivate.h new file mode 100644 index 0000000..5f5ea68 --- /dev/null +++ b/WebKit/mac/Misc/WebNSDataExtrasPrivate.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@interface NSData (WebKitExtras) + +-(NSString *)_webkit_guessedMIMEType; + +@end diff --git a/WebKit/mac/Misc/WebNSDictionaryExtras.h b/WebKit/mac/Misc/WebNSDictionaryExtras.h new file mode 100644 index 0000000..57d868a --- /dev/null +++ b/WebKit/mac/Misc/WebNSDictionaryExtras.h @@ -0,0 +1,46 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@interface NSDictionary (WebNSDictionaryExtras) +- (int)_webkit_intForKey:(id)key; +- (NSString *)_webkit_stringForKey:(id)key; // Returns nil if the value is not an NSString. + +// Searches for the full MIME type, then the prefix (e.g., "text/" for "text/html") +- (id)_webkit_objectForMIMEType:(NSString *)MIMEType; +@end + +@interface NSMutableDictionary (WebNSDictionaryExtras) +- (void)_webkit_setObject:(id)object forUncopiedKey:(id)key; +- (void)_webkit_setInt:(int)value forKey:(id)key; +- (void)_webkit_setFloat:(float)value forKey:(id)key; +- (void)_webkit_setBool:(BOOL)value forKey:(id)key; +- (void)_webkit_setUnsignedLongLong:(unsigned long long)value forKey:(id)key; +@end + diff --git a/WebKit/mac/Misc/WebNSDictionaryExtras.m b/WebKit/mac/Misc/WebNSDictionaryExtras.m new file mode 100644 index 0000000..665db22 --- /dev/null +++ b/WebKit/mac/Misc/WebNSDictionaryExtras.m @@ -0,0 +1,107 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebNSDataExtras.h> + +#import <wtf/Assertions.h> + +@implementation NSDictionary (WebNSDictionaryExtras) +-(NSNumber *)_webkit_numberForKey:(id)key +{ + id object = [self objectForKey:key]; + return [object isKindOfClass:[NSNumber class]] ? object : nil; +} + +-(int)_webkit_intForKey:(NSString *)key +{ + NSNumber *number = [self _webkit_numberForKey:key]; + return number == nil ? 0 : [number intValue]; +} + +-(NSString *)_webkit_stringForKey:(id)key +{ + id object = [self objectForKey:key]; + return [object isKindOfClass:[NSString class]] ? object : nil; +} + +-(id)_webkit_objectForMIMEType:(NSString *)MIMEType +{ + id result; + NSRange slashRange; + + result = [self objectForKey:MIMEType]; + if (result) { + return result; + } + + slashRange = [MIMEType rangeOfString:@"/"]; + if (slashRange.location == NSNotFound) { + return nil; + } + + return [self objectForKey:[MIMEType substringToIndex:slashRange.location + 1]]; +} + +@end + +@implementation NSMutableDictionary (WebNSDictionaryExtras) +-(void)_webkit_setObject:(id)object forUncopiedKey:(id)key +{ + CFDictionarySetValue((CFMutableDictionaryRef)self, key, object); +} + +-(void)_webkit_setInt:(int)value forKey:(id)key +{ + NSNumber *object = [[NSNumber alloc] initWithInt:value]; + [self setObject:object forKey:key]; + [object release]; +} + +-(void)_webkit_setFloat:(float)value forKey:(id)key +{ + NSNumber *object = [[NSNumber alloc] initWithFloat:value]; + [self setObject:object forKey:key]; + [object release]; +} + +-(void)_webkit_setBool:(BOOL)value forKey:(id)key +{ + NSNumber *object = [[NSNumber alloc] initWithBool:value]; + [self setObject:object forKey:key]; + [object release]; +} + +- (void)_webkit_setUnsignedLongLong:(unsigned long long)value forKey:(id)key +{ + NSNumber *object = [[NSNumber alloc] initWithUnsignedLongLong:value]; + [self setObject:object forKey:key]; + [object release]; +} + +@end + diff --git a/WebKit/mac/Misc/WebNSEventExtras.h b/WebKit/mac/Misc/WebNSEventExtras.h new file mode 100644 index 0000000..e35ff52 --- /dev/null +++ b/WebKit/mac/Misc/WebNSEventExtras.h @@ -0,0 +1,41 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <AppKit/AppKit.h> + +@interface NSEvent (WebExtras) + +-(BOOL)_web_isKeyEvent:(unichar)key; + +-(BOOL)_web_isDeleteKeyEvent; +-(BOOL)_web_isEscapeKeyEvent; +-(BOOL)_web_isOptionTabKeyEvent; +-(BOOL)_web_isReturnOrEnterKeyEvent; +-(BOOL)_web_isTabKeyEvent; + +@end diff --git a/WebKit/mac/Misc/WebNSEventExtras.m b/WebKit/mac/Misc/WebNSEventExtras.m new file mode 100644 index 0000000..60fb3cf --- /dev/null +++ b/WebKit/mac/Misc/WebNSEventExtras.m @@ -0,0 +1,82 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebNSEventExtras.h> + +@implementation NSEvent (WebExtras) + +-(BOOL)_web_isKeyEvent:(unichar)key +{ + int type = [self type]; + if (type != NSKeyDown && type != NSKeyUp) + return NO; + + NSString *chars = [self charactersIgnoringModifiers]; + if ([chars length] != 1) + return NO; + + unichar c = [chars characterAtIndex:0]; + if (c != key) + return NO; + + return YES; +} + +- (BOOL)_web_isDeleteKeyEvent +{ + const unichar deleteKey = NSDeleteCharacter; + const unichar deleteForwardKey = NSDeleteFunctionKey; + return [self _web_isKeyEvent:deleteKey] || [self _web_isKeyEvent:deleteForwardKey]; +} + +- (BOOL)_web_isEscapeKeyEvent +{ + const unichar escapeKey = 0x001b; + return [self _web_isKeyEvent:escapeKey]; +} + +- (BOOL)_web_isOptionTabKeyEvent +{ + return ([self modifierFlags] & NSAlternateKeyMask) && [self _web_isTabKeyEvent]; +} + +- (BOOL)_web_isReturnOrEnterKeyEvent +{ + const unichar enterKey = NSEnterCharacter; + const unichar returnKey = NSCarriageReturnCharacter; + return [self _web_isKeyEvent:enterKey] || [self _web_isKeyEvent:returnKey]; +} + +- (BOOL)_web_isTabKeyEvent +{ + const unichar tabKey = 0x0009; + const unichar shiftTabKey = 0x0019; + return [self _web_isKeyEvent:tabKey] || [self _web_isKeyEvent:shiftTabKey]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSFileManagerExtras.h b/WebKit/mac/Misc/WebNSFileManagerExtras.h new file mode 100644 index 0000000..d6e26ee --- /dev/null +++ b/WebKit/mac/Misc/WebNSFileManagerExtras.h @@ -0,0 +1,54 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +#define WEB_UREAD (00400) /* Read by owner */ +#define WEB_UWRITE (00200) /* Write by owner */ +#define WEB_UEXEC (00100) /* Execute/Search by owner */ + +@interface NSFileManager (WebNSFileManagerExtras) + +- (void)_webkit_backgroundRemoveFileAtPath:(NSString *)path; +- (void)_webkit_backgroundRemoveLeftoverFiles:(NSString *)path; +- (BOOL)_webkit_removeFileOnlyAtPath:(NSString *)path; +- (void)_webkit_setMetadataURL:(NSString *)URLString referrer:(NSString *)referrer atPath:(NSString *)path; +- (NSString *)_webkit_startupVolumeName; +- (NSString *)_webkit_pathWithUniqueFilenameForPath:(NSString *)path; + +@end + + +#ifdef BUILDING_ON_TIGER +@interface NSFileManager (WebNSFileManagerTigerForwardCompatibility) +- (NSArray *)contentsOfDirectoryAtPath:(NSString *)path error:(NSError **)error; +- (BOOL)moveItemAtPath:(NSString *)srcPath toPath:(NSString *)dstPath error:(NSError **)error; +- (BOOL)removeItemAtPath:(NSString *)path error:(NSError **)error; +- (NSDictionary *)attributesOfFileSystemForPath:(NSString *)path error:(NSError **)error; +@end +#endif diff --git a/WebKit/mac/Misc/WebNSFileManagerExtras.m b/WebKit/mac/Misc/WebNSFileManagerExtras.m new file mode 100644 index 0000000..0c10725 --- /dev/null +++ b/WebKit/mac/Misc/WebNSFileManagerExtras.m @@ -0,0 +1,238 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebNSFileManagerExtras.h> + +#import <WebKit/WebKitNSStringExtras.h> +#import <WebKitSystemInterface.h> +#import <wtf/Assertions.h> + +#import <sys/mount.h> + +@implementation NSFileManager (WebNSFileManagerExtras) + +- (BOOL)_webkit_removeFileOnlyAtPath:(NSString *)path +{ + struct statfs buf; + BOOL result = unlink([path fileSystemRepresentation]) == 0; + + // For mysterious reasons, MNT_DOVOLFS is the flag for "supports resource fork" + if ((statfs([path fileSystemRepresentation], &buf) == 0) && !(buf.f_flags & MNT_DOVOLFS)) { + NSString *lastPathComponent = [path lastPathComponent]; + if ([lastPathComponent length] != 0 && ![lastPathComponent isEqualToString:@"/"]) { + NSString *resourcePath = [[path stringByDeletingLastPathComponent] stringByAppendingString:[@"._" stringByAppendingString:lastPathComponent]]; + if (unlink([resourcePath fileSystemRepresentation]) != 0) { + result = NO; + } + } + } + + return result; +} + +- (void)_webkit_backgroundRemoveFileAtPath:(NSString *)path +{ + NSFileManager *manager; + NSString *moveToSubpath; + NSString *moveToPath; + int i; + + manager = [NSFileManager defaultManager]; + + i = 0; + moveToSubpath = [path stringByDeletingLastPathComponent]; + do { + moveToPath = [NSString stringWithFormat:@"%@/.tmp%d", moveToSubpath, i]; + i++; + } while ([manager fileExistsAtPath:moveToPath]); + + if ([manager moveItemAtPath:path toPath:moveToPath error:NULL]) + [NSThread detachNewThreadSelector:@selector(_performRemoveFileAtPath:) toTarget:self withObject:moveToPath]; +} + +- (void)_webkit_backgroundRemoveLeftoverFiles:(NSString *)path +{ + NSFileManager *manager; + NSString *leftoverSubpath; + NSString *leftoverPath; + int i; + + manager = [NSFileManager defaultManager]; + leftoverSubpath = [path stringByDeletingLastPathComponent]; + + i = 0; + while (1) { + leftoverPath = [NSString stringWithFormat:@"%@/.tmp%d", leftoverSubpath, i]; + if (![manager fileExistsAtPath:leftoverPath]) { + break; + } + [NSThread detachNewThreadSelector:@selector(_performRemoveFileAtPath:) toTarget:self withObject:leftoverPath]; + i++; + } +} + +- (NSString *)_webkit_carbonPathForPath:(NSString *)posixPath +{ + OSStatus error; + FSRef ref, rootRef, parentRef; + FSCatalogInfo info; + NSMutableArray *carbonPathPieces; + HFSUniStr255 nameString; + + // Make an FSRef. + error = FSPathMakeRef((const UInt8 *)[posixPath fileSystemRepresentation], &ref, NULL); + if (error != noErr) { + return nil; + } + + // Get volume refNum. + error = FSGetCatalogInfo(&ref, kFSCatInfoVolume, &info, NULL, NULL, NULL); + if (error != noErr) { + return nil; + } + + // Get root directory FSRef. + error = FSGetVolumeInfo(info.volume, 0, NULL, kFSVolInfoNone, NULL, NULL, &rootRef); + if (error != noErr) { + return nil; + } + + // Get the pieces of the path. + carbonPathPieces = [NSMutableArray array]; + for (;;) { + error = FSGetCatalogInfo(&ref, kFSCatInfoNone, NULL, &nameString, NULL, &parentRef); + if (error != noErr) { + return nil; + } + [carbonPathPieces insertObject:[NSString stringWithCharacters:nameString.unicode length:nameString.length] atIndex:0]; + if (FSCompareFSRefs(&ref, &rootRef) == noErr) { + break; + } + ref = parentRef; + } + + // Volume names need trailing : character. + if ([carbonPathPieces count] == 1) { + [carbonPathPieces addObject:@""]; + } + + return [carbonPathPieces componentsJoinedByString:@":"]; +} + +- (void)_webkit_setMetadataURL:(NSString *)URLString referrer:(NSString *)referrer atPath:(NSString *)path +{ + ASSERT(URLString); + ASSERT(path); + WKSetMetadataURL(URLString, referrer, path); +} + +- (NSString *)_webkit_startupVolumeName +{ + NSString *path = [self _webkit_carbonPathForPath:@"/"]; + return [path substringToIndex:[path length]-1]; +} + +- (NSString *)_webkit_pathWithUniqueFilenameForPath:(NSString *)path +{ + // "Fix" the filename of the path. + NSString *filename = [[path lastPathComponent] _webkit_filenameByFixingIllegalCharacters]; + path = [[path stringByDeletingLastPathComponent] stringByAppendingPathComponent:filename]; + + NSFileManager *fileManager = [NSFileManager defaultManager]; + if ([fileManager fileExistsAtPath:path]) { + // Don't overwrite existing file by appending "-n", "-n.ext" or "-n.ext.ext" to the filename. + NSString *extensions = nil; + NSString *pathWithoutExtensions; + NSString *lastPathComponent = [path lastPathComponent]; + NSRange periodRange = [lastPathComponent rangeOfString:@"."]; + + if (periodRange.location == NSNotFound) { + pathWithoutExtensions = path; + } else { + extensions = [lastPathComponent substringFromIndex:periodRange.location + 1]; + lastPathComponent = [lastPathComponent substringToIndex:periodRange.location]; + pathWithoutExtensions = [[path stringByDeletingLastPathComponent] stringByAppendingPathComponent:lastPathComponent]; + } + + NSString *pathWithAppendedNumber; + unsigned i; + + for (i = 1; 1; i++) { + pathWithAppendedNumber = [NSString stringWithFormat:@"%@-%d", pathWithoutExtensions, i]; + path = [extensions length] ? [pathWithAppendedNumber stringByAppendingPathExtension:extensions] : pathWithAppendedNumber; + if (![fileManager fileExistsAtPath:path]) { + break; + } + } + } + + return path; +} + +@end + + +#ifdef BUILDING_ON_TIGER +@implementation NSFileManager (WebNSFileManagerTigerForwardCompatibility) + +- (NSArray *)contentsOfDirectoryAtPath:(NSString *)path error:(NSError **)error +{ + // We don't report errors via the NSError* output parameter, so ensure that the caller does not expect us to do so. + ASSERT_ARG(error, !error); + + return [self directoryContentsAtPath:path]; +} + +- (NSDictionary *)attributesOfFileSystemForPath:(NSString *)path error:(NSError **)error +{ + // We don't report errors via the NSError* output parameter, so ensure that the caller does not expect us to do so. + ASSERT_ARG(error, !error); + + return [self fileSystemAttributesAtPath:path]; +} + +- (BOOL)moveItemAtPath:(NSString *)srcPath toPath:(NSString *)dstPath error:(NSError **)error +{ + // The implementation of moveItemAtPath:toPath:error: interacts with the NSFileManager's delegate. + // We are not matching that behaviour at the moment, but it should not be a problem as any client + // expecting that would need to call setDelegate: first which will generate a compile-time warning, + // as that method is not available on Tiger. + return [self movePath:srcPath toPath:dstPath handler:nil]; +} + +- (BOOL)removeItemAtPath:(NSString *)path error:(NSError **)error +{ + // The implementation of removeItemAtPath:error: interacts with the NSFileManager's delegate. + // We are not matching that behaviour at the moment, but it should not be a problem as any client + // expecting that would need to call setDelegate: first which will generate a compile-time warning, + // as that method is not available on Tiger. + return [self removeFileAtPath:path handler:nil]; +} + +@end +#endif diff --git a/WebKit/mac/Misc/WebNSImageExtras.h b/WebKit/mac/Misc/WebNSImageExtras.h new file mode 100644 index 0000000..b8ac5b5 --- /dev/null +++ b/WebKit/mac/Misc/WebNSImageExtras.h @@ -0,0 +1,40 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + +@interface NSImage (WebExtras) + +- (void)_web_scaleToMaxSize:(NSSize)size; + +- (void)_web_dissolveToFraction:(float)delta; + +// Debug method. Saves an image and opens it in the preferred TIFF viewing application. +- (void)_web_saveAndOpen; + +@end diff --git a/WebKit/mac/Misc/WebNSImageExtras.m b/WebKit/mac/Misc/WebNSImageExtras.m new file mode 100644 index 0000000..7124f85 --- /dev/null +++ b/WebKit/mac/Misc/WebNSImageExtras.m @@ -0,0 +1,91 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebNSImageExtras.h> + +#import <WebKit/WebKitLogging.h> + +@implementation NSImage (WebExtras) + +- (void)_web_scaleToMaxSize:(NSSize)size +{ + float heightResizeDelta = 0.0f, widthResizeDelta = 0.0f, resizeDelta = 0.0f; + NSSize originalSize = [self size]; + + if(originalSize.width > size.width){ + widthResizeDelta = size.width / originalSize.width; + resizeDelta = widthResizeDelta; + } + + if(originalSize.height > size.height){ + heightResizeDelta = size.height / originalSize.height; + if((resizeDelta == 0.0) || (resizeDelta > heightResizeDelta)){ + resizeDelta = heightResizeDelta; + } + } + + if(resizeDelta > 0.0){ + NSSize newSize = NSMakeSize((originalSize.width * resizeDelta), (originalSize.height * resizeDelta)); + [self setScalesWhenResized:YES]; + [self setSize:newSize]; + } +} + +- (void)_web_dissolveToFraction:(float)delta +{ + NSImage *dissolvedImage = [[NSImage alloc] initWithSize:[self size]]; + + NSPoint point = [self isFlipped] ? NSMakePoint(0, [self size].height) : NSZeroPoint; + + // In this case the dragging image is always correct. + [dissolvedImage setFlipped:[self isFlipped]]; + + [dissolvedImage lockFocus]; + [self dissolveToPoint:point fraction: delta]; + [dissolvedImage unlockFocus]; + + [self lockFocus]; + [dissolvedImage compositeToPoint:point operation:NSCompositeCopy]; + [self unlockFocus]; + + [dissolvedImage release]; +} + +- (void)_web_saveAndOpen +{ + char path[] = "/tmp/XXXXXX.tiff"; + int fd = mkstemps(path, 5); + if (fd != -1) { + NSData *data = [self TIFFRepresentation]; + write(fd, [data bytes], [data length]); + close(fd); + [[NSWorkspace sharedWorkspace] openFile:[NSString stringWithUTF8String:path]]; + } +} + +@end diff --git a/WebKit/mac/Misc/WebNSNotificationCenterExtras.h b/WebKit/mac/Misc/WebNSNotificationCenterExtras.h new file mode 100644 index 0000000..1a2e16c --- /dev/null +++ b/WebKit/mac/Misc/WebNSNotificationCenterExtras.h @@ -0,0 +1,39 @@ +/* + * Copyright (C) 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSNotificationCenterExtras.h" + +@interface NSNotificationCenter (WebNSNotificationCenterExtras) + +- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object; +- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo; +- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo waitUntilDone:(BOOL)wait; + ++ (void)_postNotificationName:(NSDictionary *)info; + +@end diff --git a/WebKit/mac/Misc/WebNSNotificationCenterExtras.m b/WebKit/mac/Misc/WebNSNotificationCenterExtras.m new file mode 100644 index 0000000..bc5b4ed --- /dev/null +++ b/WebKit/mac/Misc/WebNSNotificationCenterExtras.m @@ -0,0 +1,69 @@ +/* + * Copyright (C) 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSNotificationCenterExtras.h" + +@implementation NSNotificationCenter (WebNSNotificationCenterExtras) + +- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object +{ + [self postNotificationOnMainThreadWithName:name object:object userInfo:nil waitUntilDone:NO]; +} + +- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo +{ + [self postNotificationOnMainThreadWithName:name object:object userInfo:userInfo waitUntilDone:NO]; +} + +- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo waitUntilDone:(BOOL)wait +{ + NSMutableDictionary *info = [[NSMutableDictionary alloc] initWithCapacity:3]; + if (name) + [info setObject:name forKey:@"name"]; + + if (object) + [info setObject:object forKey:@"object"]; + + if (userInfo) + [info setObject:userInfo forKey:@"userInfo"]; + + [[self class] performSelectorOnMainThread:@selector(_postNotificationName:) withObject:info waitUntilDone:wait]; +} + ++ (void)_postNotificationName:(NSDictionary *)info +{ + NSString *name = [info objectForKey:@"name"]; + id object = [info objectForKey:@"object"]; + NSDictionary *userInfo = [info objectForKey:@"userInfo"]; + + [[self defaultCenter] postNotificationName:name object:object userInfo:userInfo]; + + [info release]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSObjectExtras.h b/WebKit/mac/Misc/WebNSObjectExtras.h new file mode 100644 index 0000000..8029825 --- /dev/null +++ b/WebKit/mac/Misc/WebNSObjectExtras.h @@ -0,0 +1,54 @@ +/* + * Copyright (C) 2005, 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> +#import <objc/objc-class.h> +#import <objc/objc.h> + +// Use WebCFAutorelease to return an object made by a CoreFoundation +// "create" or "copy" function as an autoreleased and garbage collected +// object. CF objects need to be "made collectable" for autorelease to work +// properly under GC. +static inline id WebCFAutorelease(CFTypeRef obj) +{ + if (obj) + CFMakeCollectable(obj); + [(id)obj autorelease]; + return (id)obj; +} + +#if !(defined(OBJC_API_VERSION) && OBJC_API_VERSION > 0) + +static inline IMP method_setImplementation(Method m, IMP i) +{ + IMP oi = m->method_imp; + m->method_imp = i; + return oi; +} + +#endif diff --git a/WebKit/mac/Misc/WebNSPasteboardExtras.h b/WebKit/mac/Misc/WebNSPasteboardExtras.h new file mode 100644 index 0000000..b994512 --- /dev/null +++ b/WebKit/mac/Misc/WebNSPasteboardExtras.h @@ -0,0 +1,89 @@ +/* + * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@class DOMElement; +@class WebArchive; +@class WebHTMLView; + +#ifdef __cplusplus +extern "C" { +#endif + +extern NSString *WebURLPboardType; +extern NSString *WebURLNamePboardType; + +@interface NSPasteboard (WebExtras) + +// Returns the array of types that _web_writeURL:andTitle: handles. ++ (NSArray *)_web_writableTypesForURL; + +// Returns the array of types that _web_writeImage handles. ++ (NSArray *)_web_writableTypesForImageIncludingArchive:(BOOL)hasArchive; + +// Returns the array of drag types that _web_bestURL handles; note that the presence +// of one or more of these drag types on the pasteboard is not a guarantee that +// _web_bestURL will return a non-nil result. ++ (NSArray *)_web_dragTypesForURL; + +// Finds the best URL from the data on the pasteboard, giving priority to http and https URLs +- (NSURL *)_web_bestURL; + +// Writes the URL to the pasteboard with the passed types. +- (void)_web_writeURL:(NSURL *)URL andTitle:(NSString *)title types:(NSArray *)types; + +// Sets the text on the NSFindPboard. Returns the new changeCount for the NSFindPboard. ++ (int)_web_setFindPasteboardString:(NSString *)string withOwner:(id)owner; + +// Writes a file wrapper to the pasteboard as an RTFD attachment. +// NSRTFDPboardType must be declared on the pasteboard before calling this method. +- (void)_web_writeFileWrapperAsRTFDAttachment:(NSFileWrapper *)wrapper; + +// Writes an image, URL and other optional types to the pasteboard. +- (void)_web_writeImage:(NSImage *)image + element:(DOMElement*)element + URL:(NSURL *)URL + title:(NSString *)title + archive:(WebArchive *)archive + types:(NSArray *)types + source:(WebHTMLView *)source; + +- (id)_web_declareAndWriteDragImageForElement:(DOMElement *)element + URL:(NSURL *)URL + title:(NSString *)title + archive:(WebArchive *)archive + source:(WebHTMLView *)source; + +- (void)_web_writePromisedRTFDFromArchive:(WebArchive*)archive containsImage:(BOOL)containsImage; + +@end + +#ifdef __cplusplus +} +#endif diff --git a/WebKit/mac/Misc/WebNSPasteboardExtras.mm b/WebKit/mac/Misc/WebNSPasteboardExtras.mm new file mode 100644 index 0000000..b84542a --- /dev/null +++ b/WebKit/mac/Misc/WebNSPasteboardExtras.mm @@ -0,0 +1,281 @@ +/* + * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSPasteboardExtras.h" + +#import "WebArchive.h" +#import "WebFrameInternal.h" +#import "WebHTMLViewInternal.h" +#import "WebNSURLExtras.h" +#import "WebResourcePrivate.h" +#import "WebURLsWithTitles.h" +#import "WebViewPrivate.h" +#import <WebCore/Element.h> +#import <WebCore/MIMETypeRegistry.h> +#import <WebCore/RenderImage.h> +#import <WebKit/DOMExtensions.h> +#import <WebKit/DOMPrivate.h> +#import <wtf/Assertions.h> +#import <wtf/RetainPtr.h> +#import <WebKitSystemInterface.h> + +@interface NSFilePromiseDragSource : NSObject +- initWithSource:(id)draggingSource; +- (void)setTypes:(NSArray *)types onPasteboard:(NSPasteboard *)pboard; +@end + +using namespace WebCore; + +NSString *WebURLPboardType = @"public.url"; +NSString *WebURLNamePboardType = @"public.url-name"; + +@implementation NSPasteboard (WebExtras) + ++ (NSArray *)_web_writableTypesForURL +{ + static RetainPtr<NSArray> types; + if (!types) { + types = [[NSArray alloc] initWithObjects: + WebURLsWithTitlesPboardType, + NSURLPboardType, + WebURLPboardType, + WebURLNamePboardType, + NSStringPboardType, + nil]; + } + return types.get(); +} + +static NSArray *_writableTypesForImageWithoutArchive (void) +{ + static RetainPtr<NSMutableArray> types; + if (types == nil) { + types = [[NSMutableArray alloc] initWithObjects:NSTIFFPboardType, nil]; + [types.get() addObjectsFromArray:[NSPasteboard _web_writableTypesForURL]]; + } + return types.get(); +} + +static NSArray *_writableTypesForImageWithArchive (void) +{ + static RetainPtr<NSMutableArray> types; + if (types == nil) { + types = [_writableTypesForImageWithoutArchive() mutableCopy]; + [types.get() addObject:NSRTFDPboardType]; + [types.get() addObject:WebArchivePboardType]; + } + return types.get(); +} + ++ (NSArray *)_web_writableTypesForImageIncludingArchive:(BOOL)hasArchive +{ + return hasArchive + ? _writableTypesForImageWithArchive() + : _writableTypesForImageWithoutArchive(); +} + ++ (NSArray *)_web_dragTypesForURL +{ + return [NSArray arrayWithObjects: + WebURLsWithTitlesPboardType, + NSURLPboardType, + WebURLPboardType, + WebURLNamePboardType, + NSStringPboardType, + NSFilenamesPboardType, + nil]; +} + +- (NSURL *)_web_bestURL +{ + NSArray *types = [self types]; + + if ([types containsObject:NSURLPboardType]) { + NSURL *URLFromPasteboard = [NSURL URLFromPasteboard:self]; + NSString *scheme = [URLFromPasteboard scheme]; + if ([scheme isEqualToString:@"http"] || [scheme isEqualToString:@"https"]) { + return [URLFromPasteboard _webkit_canonicalize]; + } + } + + if ([types containsObject:NSStringPboardType]) { + NSString *URLString = [self stringForType:NSStringPboardType]; + if ([URLString _webkit_looksLikeAbsoluteURL]) { + NSURL *URL = [[NSURL _web_URLWithUserTypedString:URLString] _webkit_canonicalize]; + if (URL) { + return URL; + } + } + } + + if ([types containsObject:NSFilenamesPboardType]) { + NSArray *files = [self propertyListForType:NSFilenamesPboardType]; + if ([files count] == 1) { + NSString *file = [files objectAtIndex:0]; + BOOL isDirectory; + if([[NSFileManager defaultManager] fileExistsAtPath:file isDirectory:&isDirectory] && !isDirectory){ + return [[NSURL fileURLWithPath:file] _webkit_canonicalize]; + } + } + } + + return nil; +} + +- (void)_web_writeURL:(NSURL *)URL andTitle:(NSString *)title types:(NSArray *)types +{ + ASSERT(URL); + + if ([title length] == 0) { + title = [[URL path] lastPathComponent]; + if ([title length] == 0) + title = [URL _web_userVisibleString]; + } + + if ([types containsObject:NSURLPboardType]) + [URL writeToPasteboard:self]; + if ([types containsObject:WebURLPboardType]) + [self setString:[URL _web_originalDataAsString] forType:WebURLPboardType]; + if ([types containsObject:WebURLNamePboardType]) + [self setString:title forType:WebURLNamePboardType]; + if ([types containsObject:NSStringPboardType]) + [self setString:[URL _web_userVisibleString] forType:NSStringPboardType]; + if ([types containsObject:WebURLsWithTitlesPboardType]) + [WebURLsWithTitles writeURLs:[NSArray arrayWithObject:URL] andTitles:[NSArray arrayWithObject:title] toPasteboard:self]; +} + ++ (int)_web_setFindPasteboardString:(NSString *)string withOwner:(id)owner +{ + NSPasteboard *findPasteboard = [NSPasteboard pasteboardWithName:NSFindPboard]; + [findPasteboard declareTypes:[NSArray arrayWithObject:NSStringPboardType] owner:owner]; + [findPasteboard setString:string forType:NSStringPboardType]; + return [findPasteboard changeCount]; +} + +- (void)_web_writeFileWrapperAsRTFDAttachment:(NSFileWrapper *)wrapper +{ + NSTextAttachment *attachment = [[NSTextAttachment alloc] initWithFileWrapper:wrapper]; + + NSAttributedString *string = [NSAttributedString attributedStringWithAttachment:attachment]; + [attachment release]; + + NSData *RTFDData = [string RTFDFromRange:NSMakeRange(0, [string length]) documentAttributes:nil]; + [self setData:RTFDData forType:NSRTFDPboardType]; +} + + +- (void)_web_writePromisedRTFDFromArchive:(WebArchive*)archive containsImage:(BOOL)containsImage +{ + ASSERT(archive); + // This image data is either the only subresource of an archive (HTML image case) + // or the main resource (standalone image case). + NSArray *subresources = [archive subresources]; + WebResource *resource = [archive mainResource]; + if (containsImage && [subresources count] > 0 + && MIMETypeRegistry::isSupportedImageResourceMIMEType([[subresources objectAtIndex:0] MIMEType])) + resource = (WebResource *)[subresources objectAtIndex:0]; + ASSERT(resource != nil); + + ASSERT(!containsImage || MIMETypeRegistry::isSupportedImageResourceMIMEType([resource MIMEType])); + if (!containsImage || MIMETypeRegistry::isSupportedImageResourceMIMEType([resource MIMEType])) + [self _web_writeFileWrapperAsRTFDAttachment:[resource _fileWrapperRepresentation]]; + +} + +CachedImage* imageFromElement(DOMElement *domElement) { + Element* element = core(domElement); + if (!element) + return 0; + + RenderObject* renderer = element->renderer(); + RenderImage* imageRenderer = static_cast<RenderImage*>(renderer); + if (!imageRenderer->cachedImage() || imageRenderer->cachedImage()->errorOccurred()) + return 0; + return imageRenderer->cachedImage(); +} + +- (void)_web_writeImage:(NSImage *)image + element:(DOMElement *)element + URL:(NSURL *)URL + title:(NSString *)title + archive:(WebArchive *)archive + types:(NSArray *)types + source:(WebHTMLView *)source +{ + ASSERT(image || element); + ASSERT(URL); + + [self _web_writeURL:URL andTitle:title types:types]; + + if ([types containsObject:NSTIFFPboardType]) { + if (image) + [self setData:[image TIFFRepresentation] forType:NSTIFFPboardType]; + else if (source && element) + [source setPromisedDragTIFFDataSource:imageFromElement(element)]; + else if (element) + [self setData:[element _imageTIFFRepresentation] forType:NSTIFFPboardType]; + } + + if (archive) + if ([types containsObject:WebArchivePboardType]) + [self setData:[archive data] forType:WebArchivePboardType]; + else { + // We should not have declared types that we aren't going to write (4031826). + ASSERT(![types containsObject:NSRTFDPboardType]); + ASSERT(![types containsObject:WebArchivePboardType]); + } +} + +- (id)_web_declareAndWriteDragImageForElement:(DOMElement *)element + URL:(NSURL *)URL + title:(NSString *)title + archive:(WebArchive *)archive + source:(WebHTMLView *)source +{ + ASSERT(self == [NSPasteboard pasteboardWithName:NSDragPboard]); + + NSMutableArray *types = [[NSMutableArray alloc] initWithObjects:NSFilesPromisePboardType, nil]; + [types addObjectsFromArray:[NSPasteboard _web_writableTypesForImageIncludingArchive:(archive != nil)]]; + [self declareTypes:types owner:source]; + [self _web_writeImage:nil element:element URL:URL title:title archive:archive types:types source:source]; + [types release]; + + NSString *extension = @""; + if (RenderObject* renderer = core(element)->renderer()) + if (renderer->isImage()) + if (CachedImage* image = static_cast<RenderImage*>(renderer)->cachedImage()) + extension = WKGetPreferredExtensionForMIMEType(image->response().mimeType()); + + NSArray *extensions = [[NSArray alloc] initWithObjects:extension, nil]; + [self setPropertyList:extensions forType:NSFilesPromisePboardType]; + [extensions release]; + + return source; +} + +@end diff --git a/WebKit/mac/Misc/WebNSPrintOperationExtras.h b/WebKit/mac/Misc/WebNSPrintOperationExtras.h new file mode 100644 index 0000000..44eb3df --- /dev/null +++ b/WebKit/mac/Misc/WebNSPrintOperationExtras.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + +@interface NSPrintOperation (WebKitExtras) + +- (float)_web_pageSetupScaleFactor; + +@end diff --git a/WebKit/mac/Misc/WebNSPrintOperationExtras.m b/WebKit/mac/Misc/WebNSPrintOperationExtras.m new file mode 100644 index 0000000..4c45f17 --- /dev/null +++ b/WebKit/mac/Misc/WebNSPrintOperationExtras.m @@ -0,0 +1,38 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSPrintOperationExtras.h" + +@implementation NSPrintOperation (WebKitExtras) + +- (float)_web_pageSetupScaleFactor +{ + return [[[[self printInfo] dictionary] objectForKey:NSPrintScalingFactor] floatValue]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSURLExtras.h b/WebKit/mac/Misc/WebNSURLExtras.h new file mode 100644 index 0000000..f8823b9 --- /dev/null +++ b/WebKit/mac/Misc/WebNSURLExtras.h @@ -0,0 +1,95 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@interface NSURL (WebNSURLExtras) + ++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string; ++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string relativeToURL:(NSURL *)URL; + ++ (NSURL *)_web_URLWithDataAsString:(NSString *)string; ++ (NSURL *)_web_URLWithDataAsString:(NSString *)string relativeToURL:(NSURL *)baseURL; + ++ (NSURL *)_web_URLWithData:(NSData *)data; ++ (NSURL *)_web_URLWithData:(NSData *)data relativeToURL:(NSURL *)baseURL; + +- (NSURL *)_web_URLWithLowercasedScheme; + +- (NSData *)_web_originalData; +- (NSString *)_web_originalDataAsString; +- (const char *)_web_URLCString; + +- (NSData *)_web_hostData; +- (NSString *)_web_hostString; + +- (NSString *)_web_userVisibleString; + +- (BOOL)_web_isEmpty; + +// FIXME: change these names back to _web_ when identically-named +// methods are removed from Foundation + +- (NSURL *)_webkit_canonicalize; +- (NSURL *)_webkit_URLByRemovingFragment; +- (NSURL *)_webkit_URLByRemovingResourceSpecifier; + +- (BOOL)_webkit_isJavaScriptURL; +- (NSString *)_webkit_scriptIfJavaScriptURL; +- (BOOL)_webkit_isFTPDirectoryURL; + +- (BOOL)_webkit_shouldLoadAsEmptyDocument; + +- (NSString *)_webkit_suggestedFilenameWithMIMEType:(NSString *)MIMEType; + +@end + +@interface NSString (WebNSURLExtras) + +- (BOOL)_web_isUserVisibleURL; + +- (BOOL)_web_hostNameNeedsDecodingWithRange:(NSRange)range; // returns NO if decodeHostNameWithRange: would return nil, but more efficient +- (BOOL)_web_hostNameNeedsEncodingWithRange:(NSRange)range; // returns NO if encodeHostNameWithRange: would return nil, but more efficient + +- (NSString *)_web_decodeHostNameWithRange:(NSRange)range; // turns funny-looking ASCII form into Unicode, returns nil if no decoding needed +- (NSString *)_web_encodeHostNameWithRange:(NSRange)range; // turns Unicode into funny-looking ASCII form, returns nil if no decoding needed + +- (NSString *)_web_decodeHostName; // turns funny-looking ASCII form into Unicode, returns self if no decoding needed, convenient cover +- (NSString *)_web_encodeHostName; // turns Unicode into funny-looking ASCII form, returns self if no decoding needed, convenient cover + +// FIXME: change these names back to _web_ when identically-named +// methods are removed from or renamed in Foundation +- (BOOL)_webkit_isJavaScriptURL; +- (BOOL)_webkit_isFTPDirectoryURL; +- (BOOL)_webkit_isFileURL; +- (BOOL)_webkit_looksLikeAbsoluteURL; +- (NSRange)_webkit_rangeOfURLScheme; +- (NSString *)_webkit_URLFragment; +- (NSString *)_webkit_scriptIfJavaScriptURL; + +@end diff --git a/WebKit/mac/Misc/WebNSURLExtras.mm b/WebKit/mac/Misc/WebNSURLExtras.mm new file mode 100644 index 0000000..b388c22 --- /dev/null +++ b/WebKit/mac/Misc/WebNSURLExtras.mm @@ -0,0 +1,1128 @@ +/* + * Copyright (C) 2005, 2007, 2008 Apple Inc. All rights reserved. + * Copyright (C) 2006 Alexey Proskuryakov (ap@nypop.com) + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSURLExtras.h" + +#import "WebKitNSStringExtras.h" +#import "WebLocalizableStrings.h" +#import "WebNSDataExtras.h" +#import "WebNSObjectExtras.h" +#import "WebSystemInterface.h" +#import <Foundation/NSURLRequest.h> +#import <WebCore/KURL.h> +#import <WebCore/LoaderNSURLExtras.h> +#import <WebKitSystemInterface.h> +#import <wtf/Assertions.h> +#import <unicode/uchar.h> +#import <unicode/uidna.h> +#import <unicode/uscript.h> + +using namespace WebCore; +using namespace WTF; + +typedef void (* StringRangeApplierFunction)(NSString *string, NSRange range, void *context); + +// Needs to be big enough to hold an IDN-encoded name. +// For host names bigger than this, we won't do IDN encoding, which is almost certainly OK. +#define HOST_NAME_BUFFER_LENGTH 2048 + +#define URL_BYTES_BUFFER_LENGTH 2048 + +static pthread_once_t IDNScriptWhiteListFileRead = PTHREAD_ONCE_INIT; +static uint32_t IDNScriptWhiteList[(USCRIPT_CODE_LIMIT + 31) / 32]; + +static inline BOOL isLookalikeCharacter(int charCode) +{ +// FIXME: Move this code down into WebCore so it can be shared with other platforms. + +// This function treats the following as unsafe, lookalike characters: +// any non-printable character, any character considered as whitespace that isn't already converted to a space by ICU, +// and any ignorable character. + +// We also considered the characters in Mozilla's blacklist (http://kb.mozillazine.org/Network.IDN.blacklist_chars), +// and included all of these characters that ICU can encode. + + if (!u_isprint(charCode) || u_isUWhiteSpace(charCode) || u_hasBinaryProperty(charCode, UCHAR_DEFAULT_IGNORABLE_CODE_POINT)) + return YES; + + switch (charCode) { + case 0x01C3: /* LATIN LETTER RETROFLEX CLICK */ + case 0x0337: /* COMBINING SHORT SOLIDUS OVERLAY */ + case 0x0338: /* COMBINING LONG SOLIDUS OVERLAY */ + case 0x05B4: /* HEBREW POINT HIRIQ */ + case 0x05BC: /* HEBREW POINT DAGESH OR MAPIQ */ + case 0x05C3: /* HEBREW PUNCTUATION SOF PASUQ */ + case 0x05F4: /* HEBREW PUNCTUATION GERSHAYIM */ + case 0x0660: /* ARABIC INDIC DIGIT ZERO */ + case 0x06D4: /* ARABIC FULL STOP */ + case 0x06F0: /* EXTENDED ARABIC INDIC DIGIT ZERO */ + case 0x2027: /* HYPHENATION POINT */ + case 0x2039: /* SINGLE LEFT-POINTING ANGLE QUOTATION MARK */ + case 0x203A: /* SINGLE RIGHT-POINTING ANGLE QUOTATION MARK */ + case 0x2044: /* FRACTION SLASH */ + case 0x2215: /* DIVISION SLASH */ + case 0x23ae: /* INTEGRAL EXTENSION */ + case 0x2571: /* BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT */ + case 0x29F8: /* BIG SOLIDUS */ + case 0x29f6: /* SOLIDUS WITH OVERBAR */ + case 0x2AFB: /* TRIPLE SOLIDUS BINARY RELATION */ + case 0x2AFD: /* DOUBLE SOLIDUS OPERATOR */ + case 0x3008: /* LEFT ANGLE BRACKET */ + case 0x3014: /* LEFT TORTOISE SHELL BRACKET */ + case 0x3015: /* RIGHT TORTOISE SHELL BRACKET */ + case 0x3033: /* VERTICAL KANA REPEAT MARK UPPER HALF */ + case 0x321D: /* PARENTHESIZED KOREAN CHARACTER OJEON */ + case 0x321E: /* PARENTHESIZED KOREAN CHARACTER O HU */ + case 0x33DF: /* SQUARE A OVER M */ + case 0xFE14: /* PRESENTATION FORM FOR VERTICAL SEMICOLON */ + case 0xFE15: /* PRESENTATION FORM FOR VERTICAL EXCLAMATION MARK */ + case 0xFE3F: /* PRESENTATION FORM FOR VERTICAL LEFT ANGLE BRACKET */ + case 0xFE5D: /* SMALL LEFT TORTOISE SHELL BRACKET */ + case 0xFE5E: /* SMALL RIGHT TORTOISE SHELL BRACKET */ + return YES; + default: + return NO; + } +} + +static char hexDigit(int i) +{ + if (i < 0 || i > 16) { + LOG_ERROR("illegal hex digit"); + return '0'; + } + int h = i; + if (h >= 10) { + h = h - 10 + 'A'; + } + else { + h += '0'; + } + return h; +} + +static BOOL isHexDigit(char c) +{ + return (c >= '0' && c <= '9') || (c >= 'A' && c <= 'F') || (c >= 'a' && c <= 'f'); +} + +static int hexDigitValue(char c) +{ + if (c >= '0' && c <= '9') { + return c - '0'; + } + if (c >= 'A' && c <= 'F') { + return c - 'A' + 10; + } + if (c >= 'a' && c <= 'f') { + return c - 'a' + 10; + } + LOG_ERROR("illegal hex digit"); + return 0; +} + +static void applyHostNameFunctionToMailToURLString(NSString *string, StringRangeApplierFunction f, void *context) +{ + // In a mailto: URL, host names come after a '@' character and end with a '>' or ',' or '?' character. + // Skip quoted strings so that characters in them don't confuse us. + // When we find a '?' character, we are past the part of the URL that contains host names. + + static NSCharacterSet *hostNameOrStringStartCharacters; + if (hostNameOrStringStartCharacters == nil) { + hostNameOrStringStartCharacters = [NSCharacterSet characterSetWithCharactersInString:@"\"@?"]; + CFRetain(hostNameOrStringStartCharacters); + } + static NSCharacterSet *hostNameEndCharacters; + if (hostNameEndCharacters == nil) { + hostNameEndCharacters = [NSCharacterSet characterSetWithCharactersInString:@">,?"]; + CFRetain(hostNameEndCharacters); + } + static NSCharacterSet *quotedStringCharacters; + if (quotedStringCharacters == nil) { + quotedStringCharacters = [NSCharacterSet characterSetWithCharactersInString:@"\"\\"]; + CFRetain(quotedStringCharacters); + } + + unsigned stringLength = [string length]; + NSRange remaining = NSMakeRange(0, stringLength); + + while (1) { + // Find start of host name or of quoted string. + NSRange hostNameOrStringStart = [string rangeOfCharacterFromSet:hostNameOrStringStartCharacters options:0 range:remaining]; + if (hostNameOrStringStart.location == NSNotFound) { + return; + } + unichar c = [string characterAtIndex:hostNameOrStringStart.location]; + remaining.location = NSMaxRange(hostNameOrStringStart); + remaining.length = stringLength - remaining.location; + + if (c == '?') { + return; + } + + if (c == '@') { + // Find end of host name. + unsigned hostNameStart = remaining.location; + NSRange hostNameEnd = [string rangeOfCharacterFromSet:hostNameEndCharacters options:0 range:remaining]; + BOOL done; + if (hostNameEnd.location == NSNotFound) { + hostNameEnd.location = stringLength; + done = YES; + } else { + remaining.location = hostNameEnd.location; + remaining.length = stringLength - remaining.location; + done = NO; + } + + // Process host name range. + f(string, NSMakeRange(hostNameStart, hostNameEnd.location - hostNameStart), context); + + if (done) { + return; + } + } else { + // Skip quoted string. + ASSERT(c == '"'); + while (1) { + NSRange escapedCharacterOrStringEnd = [string rangeOfCharacterFromSet:quotedStringCharacters options:0 range:remaining]; + if (escapedCharacterOrStringEnd.location == NSNotFound) { + return; + } + c = [string characterAtIndex:escapedCharacterOrStringEnd.location]; + remaining.location = NSMaxRange(escapedCharacterOrStringEnd); + remaining.length = stringLength - remaining.location; + + // If we are the end of the string, then break from the string loop back to the host name loop. + if (c == '"') { + break; + } + + // Skip escaped character. + ASSERT(c == '\\'); + if (remaining.length == 0) { + return; + } + remaining.location += 1; + remaining.length -= 1; + } + } + } +} + +static void applyHostNameFunctionToURLString(NSString *string, StringRangeApplierFunction f, void *context) +{ + // Find hostnames. Too bad we can't use any real URL-parsing code to do this, + // but we have to do it before doing all the %-escaping, and this is the only + // code we have that parses mailto URLs anyway. + + // Maybe we should implement this using a character buffer instead? + + if ([string _webkit_hasCaseInsensitivePrefix:@"mailto:"]) { + applyHostNameFunctionToMailToURLString(string, f, context); + return; + } + + // Find the host name in a hierarchical URL. + // It comes after a "://" sequence, with scheme characters preceding. + // If ends with the end of the string or a ":", "/", or a "?". + // If there is a "@" character, the host part is just the part after the "@". + NSRange separatorRange = [string rangeOfString:@"://"]; + if (separatorRange.location == NSNotFound) { + return; + } + + // Check that all characters before the :// are valid scheme characters. + static NSCharacterSet *nonSchemeCharacters; + if (nonSchemeCharacters == nil) { + nonSchemeCharacters = [[NSCharacterSet characterSetWithCharactersInString:@"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+-."] invertedSet]; + CFRetain(nonSchemeCharacters); + } + if ([string rangeOfCharacterFromSet:nonSchemeCharacters options:0 range:NSMakeRange(0, separatorRange.location)].location != NSNotFound) { + return; + } + + unsigned stringLength = [string length]; + + static NSCharacterSet *hostTerminators; + if (hostTerminators == nil) { + hostTerminators = [NSCharacterSet characterSetWithCharactersInString:@":/?#"]; + CFRetain(hostTerminators); + } + + // Start after the separator. + unsigned authorityStart = NSMaxRange(separatorRange); + + // Find terminating character. + NSRange hostNameTerminator = [string rangeOfCharacterFromSet:hostTerminators options:0 range:NSMakeRange(authorityStart, stringLength - authorityStart)]; + unsigned hostNameEnd = hostNameTerminator.location == NSNotFound ? stringLength : hostNameTerminator.location; + + // Find "@" for the start of the host name. + NSRange userInfoTerminator = [string rangeOfString:@"@" options:0 range:NSMakeRange(authorityStart, hostNameEnd - authorityStart)]; + unsigned hostNameStart = userInfoTerminator.location == NSNotFound ? authorityStart : NSMaxRange(userInfoTerminator); + + f(string, NSMakeRange(hostNameStart, hostNameEnd - hostNameStart), context); +} + +@implementation NSURL (WebNSURLExtras) + +static void collectRangesThatNeedMapping(NSString *string, NSRange range, void *context, BOOL encode) +{ + BOOL needsMapping = encode + ? [string _web_hostNameNeedsEncodingWithRange:range] + : [string _web_hostNameNeedsDecodingWithRange:range]; + if (!needsMapping) { + return; + } + + NSMutableArray **array = (NSMutableArray **)context; + if (*array == nil) { + *array = [[NSMutableArray alloc] init]; + } + + [*array addObject:[NSValue valueWithRange:range]]; +} + +static void collectRangesThatNeedEncoding(NSString *string, NSRange range, void *context) +{ + return collectRangesThatNeedMapping(string, range, context, YES); +} + +static void collectRangesThatNeedDecoding(NSString *string, NSRange range, void *context) +{ + return collectRangesThatNeedMapping(string, range, context, NO); +} + +static NSString *mapHostNames(NSString *string, BOOL encode) +{ + // Generally, we want to optimize for the case where there is one host name that does not need mapping. + + if (encode && [string canBeConvertedToEncoding:NSASCIIStringEncoding]) + return string; + + // Make a list of ranges that actually need mapping. + NSMutableArray *hostNameRanges = nil; + StringRangeApplierFunction f = encode + ? collectRangesThatNeedEncoding + : collectRangesThatNeedDecoding; + applyHostNameFunctionToURLString(string, f, &hostNameRanges); + if (hostNameRanges == nil) + return string; + + // Do the mapping. + NSMutableString *mutableCopy = [string mutableCopy]; + unsigned i = [hostNameRanges count]; + while (i-- != 0) { + NSRange hostNameRange = [[hostNameRanges objectAtIndex:i] rangeValue]; + NSString *mappedHostName = encode + ? [string _web_encodeHostNameWithRange:hostNameRange] + : [string _web_decodeHostNameWithRange:hostNameRange]; + [mutableCopy replaceCharactersInRange:hostNameRange withString:mappedHostName]; + } + [hostNameRanges release]; + return [mutableCopy autorelease]; +} + ++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string relativeToURL:(NSURL *)URL +{ + if (string == nil) { + return nil; + } + string = mapHostNames([string _webkit_stringByTrimmingWhitespace], YES); + + NSData *userTypedData = [string dataUsingEncoding:NSUTF8StringEncoding]; + ASSERT(userTypedData); + + const UInt8 *inBytes = static_cast<const UInt8 *>([userTypedData bytes]); + int inLength = [userTypedData length]; + if (inLength == 0) { + return [NSURL URLWithString:@""]; + } + + char *outBytes = static_cast<char *>(malloc(inLength * 3)); // large enough to %-escape every character + char *p = outBytes; + int outLength = 0; + int i; + for (i = 0; i < inLength; i++) { + UInt8 c = inBytes[i]; + if (c <= 0x20 || c >= 0x7f) { + *p++ = '%'; + *p++ = hexDigit(c >> 4); + *p++ = hexDigit(c & 0xf); + outLength += 3; + } + else { + *p++ = c; + outLength++; + } + } + + NSData *data = [NSData dataWithBytesNoCopy:outBytes length:outLength]; // adopts outBytes + return [self _web_URLWithData:data relativeToURL:URL]; +} + ++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string +{ + return [self _web_URLWithUserTypedString:string relativeToURL:nil]; +} + ++ (NSURL *)_web_URLWithDataAsString:(NSString *)string +{ + if (string == nil) { + return nil; + } + return [self _web_URLWithDataAsString:string relativeToURL:nil]; +} + ++ (NSURL *)_web_URLWithDataAsString:(NSString *)string relativeToURL:(NSURL *)baseURL +{ + if (string == nil) { + return nil; + } + string = [string _webkit_stringByTrimmingWhitespace]; + NSData *data = [string dataUsingEncoding:NSISOLatin1StringEncoding]; + return [self _web_URLWithData:data relativeToURL:baseURL]; +} + ++ (NSURL *)_web_URLWithData:(NSData *)data +{ + return [NSURL _web_URLWithData:data relativeToURL:nil]; +} + ++ (NSURL *)_web_URLWithData:(NSData *)data relativeToURL:(NSURL *)baseURL +{ + if (data == nil) + return nil; + + NSURL *result = nil; + size_t length = [data length]; + if (length > 0) { + // work around <rdar://4470771>: CFURLCreateAbsoluteURLWithBytes(.., TRUE) doesn't remove non-path components. + baseURL = [baseURL _webkit_URLByRemovingResourceSpecifier]; + + const UInt8 *bytes = static_cast<const UInt8*>([data bytes]); + // NOTE: We use UTF-8 here since this encoding is used when computing strings when returning URL components + // (e.g calls to NSURL -path). However, this function is not tolerant of illegal UTF-8 sequences, which + // could either be a malformed string or bytes in a different encoding, like shift-jis, so we fall back + // onto using ISO Latin 1 in those cases. + result = WebCFAutorelease(CFURLCreateAbsoluteURLWithBytes(NULL, bytes, length, kCFStringEncodingUTF8, (CFURLRef)baseURL, YES)); + if (!result) + result = WebCFAutorelease(CFURLCreateAbsoluteURLWithBytes(NULL, bytes, length, kCFStringEncodingISOLatin1, (CFURLRef)baseURL, YES)); + } else + result = [NSURL URLWithString:@""]; + + return result; +} + +- (NSData *)_web_originalData +{ + UInt8 *buffer = (UInt8 *)malloc(URL_BYTES_BUFFER_LENGTH); + CFIndex bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, URL_BYTES_BUFFER_LENGTH); + if (bytesFilled == -1) { + CFIndex bytesToAllocate = CFURLGetBytes((CFURLRef)self, NULL, 0); + buffer = (UInt8 *)realloc(buffer, bytesToAllocate); + bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, bytesToAllocate); + ASSERT(bytesFilled == bytesToAllocate); + } + + // buffer is adopted by the NSData + NSData *data = [NSData dataWithBytesNoCopy:buffer length:bytesFilled freeWhenDone:YES]; + + NSURL *baseURL = (NSURL *)CFURLGetBaseURL((CFURLRef)self); + if (baseURL) + return [[NSURL _web_URLWithData:data relativeToURL:baseURL] _web_originalData]; + return data; +} + +- (NSString *)_web_originalDataAsString +{ + return [[[NSString alloc] initWithData:[self _web_originalData] encoding:NSISOLatin1StringEncoding] autorelease]; +} + +static CFStringRef createStringWithEscapedUnsafeCharacters(CFStringRef string) +{ + CFIndex length = CFStringGetLength(string); + Vector<UChar, 2048> sourceBuffer(length); + CFStringGetCharacters(string, CFRangeMake(0, length), sourceBuffer.data()); + + Vector<UChar, 2048> outBuffer; + + CFIndex i = 0; + while (i < length) { + UChar32 c; + U16_NEXT(sourceBuffer, i, length, c) + + if (isLookalikeCharacter(c)) { + uint8_t utf8Buffer[4]; + CFIndex offset = 0; + UBool failure = false; + U8_APPEND(utf8Buffer, offset, 4, c, failure) + ASSERT(!failure); + + for (CFIndex j = 0; j < offset; ++j) { + outBuffer.append('%'); + outBuffer.append(hexDigit(utf8Buffer[j] >> 4)); + outBuffer.append(hexDigit(utf8Buffer[j] & 0xf)); + } + } else { + UChar utf16Buffer[2]; + CFIndex offset = 0; + UBool failure = false; + U16_APPEND(utf16Buffer, offset, 2, c, failure) + ASSERT(!failure); + for (CFIndex j = 0; j < offset; ++j) + outBuffer.append(utf16Buffer[j]); + } + } + + return CFStringCreateWithCharacters(NULL, outBuffer.data(), outBuffer.size()); +} + +- (NSString *)_web_userVisibleString +{ + NSData *data = [self _web_originalData]; + const unsigned char *before = static_cast<const unsigned char*>([data bytes]); + int length = [data length]; + + bool needsHostNameDecoding = false; + + const unsigned char *p = before; + int bufferLength = (length * 3) + 1; + char *after = static_cast<char *>(malloc(bufferLength)); // large enough to %-escape every character + char *q = after; + int i; + for (i = 0; i < length; i++) { + unsigned char c = p[i]; + // unescape escape sequences that indicate bytes greater than 0x7f + if (c == '%' && (i + 1 < length && isHexDigit(p[i + 1])) && i + 2 < length && isHexDigit(p[i + 2])) { + unsigned char u = (hexDigitValue(p[i + 1]) << 4) | hexDigitValue(p[i + 2]); + if (u > 0x7f) { + // unescape + *q++ = u; + } else { + // do not unescape + *q++ = p[i]; + *q++ = p[i + 1]; + *q++ = p[i + 2]; + } + i += 2; + } else { + *q++ = c; + + // Check for "xn--" in an efficient, non-case-sensitive, way. + if (c == '-' && i >= 3 && !needsHostNameDecoding && (q[-4] | 0x20) == 'x' && (q[-3] | 0x20) == 'n' && q[-2] == '-') + needsHostNameDecoding = true; + } + } + *q = '\0'; + + // Check string to see if it can be converted to display using UTF-8 + NSString *result = [NSString stringWithUTF8String:after]; + if (!result) { + // Could not convert to UTF-8. + // Convert characters greater than 0x7f to escape sequences. + // Shift current string to the end of the buffer + // then we will copy back bytes to the start of the buffer + // as we convert. + int afterlength = q - after; + char *p = after + bufferLength - afterlength - 1; + memmove(p, after, afterlength + 1); // copies trailing '\0' + char *q = after; + while (*p) { + unsigned char c = *p; + if (c > 0x7f) { + *q++ = '%'; + *q++ = hexDigit(c >> 4); + *q++ = hexDigit(c & 0xf); + } else { + *q++ = *p; + } + p++; + } + *q = '\0'; + result = [NSString stringWithUTF8String:after]; + } + + free(after); + + result = mapHostNames(result, !needsHostNameDecoding); + return WebCFAutorelease(createStringWithEscapedUnsafeCharacters((CFStringRef)result)); +} + +- (BOOL)_web_isEmpty +{ + if (!CFURLGetBaseURL((CFURLRef)self)) + return CFURLGetBytes((CFURLRef)self, NULL, 0) == 0; + return [[self _web_originalData] length] == 0; +} + +- (const char *)_web_URLCString +{ + NSMutableData *data = [NSMutableData data]; + [data appendData:[self _web_originalData]]; + [data appendBytes:"\0" length:1]; + return (const char *)[data bytes]; + } + +- (NSURL *)_webkit_canonicalize +{ + NSURLRequest *request = [[NSURLRequest alloc] initWithURL:self]; + Class concreteClass = WKNSURLProtocolClassForRequest(request); + if (!concreteClass) { + [request release]; + return self; + } + + // This applies NSURL's concept of canonicalization, but not KURL's concept. It would + // make sense to apply both, but when we tried that it caused a performance degradation + // (see 5315926). It might make sense to apply only the KURL concept and not the NSURL + // concept, but it's too risky to make that change for WebKit 3.0. + NSURLRequest *newRequest = [concreteClass canonicalRequestForRequest:request]; + NSURL *newURL = [newRequest URL]; + NSURL *result = [[newURL retain] autorelease]; + [request release]; + + return result; +} + +typedef struct { + NSString *scheme; + NSString *user; + NSString *password; + NSString *host; + CFIndex port; // kCFNotFound means ignore/omit + NSString *path; + NSString *query; + NSString *fragment; +} WebKitURLComponents; + +- (NSURL *)_webkit_URLByRemovingComponent:(CFURLComponentType)component +{ + CFRange fragRg = CFURLGetByteRangeForComponent((CFURLRef)self, component, NULL); + // Check to see if a fragment exists before decomposing the URL. + if (fragRg.location == kCFNotFound) + return self; + + UInt8 *urlBytes, buffer[2048]; + CFIndex numBytes = CFURLGetBytes((CFURLRef)self, buffer, 2048); + if (numBytes == -1) { + numBytes = CFURLGetBytes((CFURLRef)self, NULL, 0); + urlBytes = static_cast<UInt8*>(malloc(numBytes)); + CFURLGetBytes((CFURLRef)self, urlBytes, numBytes); + } else + urlBytes = buffer; + + NSURL *result = (NSURL *)CFMakeCollectable(CFURLCreateWithBytes(NULL, urlBytes, fragRg.location - 1, kCFStringEncodingUTF8, NULL)); + if (!result) + result = (NSURL *)CFMakeCollectable(CFURLCreateWithBytes(NULL, urlBytes, fragRg.location - 1, kCFStringEncodingISOLatin1, NULL)); + + if (urlBytes != buffer) free(urlBytes); + return result ? [result autorelease] : self; +} + +- (NSURL *)_webkit_URLByRemovingFragment +{ + return [self _webkit_URLByRemovingComponent:kCFURLComponentFragment]; +} + +- (NSURL *)_webkit_URLByRemovingResourceSpecifier +{ + return [self _webkit_URLByRemovingComponent:kCFURLComponentResourceSpecifier]; +} + +- (BOOL)_webkit_isJavaScriptURL +{ + return [[self _web_originalDataAsString] _webkit_isJavaScriptURL]; +} + +- (NSString *)_webkit_scriptIfJavaScriptURL +{ + return [[self absoluteString] _webkit_scriptIfJavaScriptURL]; +} + +- (BOOL)_webkit_isFileURL +{ + return [[self _web_originalDataAsString] _webkit_isFileURL]; +} + +- (BOOL)_webkit_isFTPDirectoryURL +{ + return [[self _web_originalDataAsString] _webkit_isFTPDirectoryURL]; +} + +- (BOOL)_webkit_shouldLoadAsEmptyDocument +{ + return [[self _web_originalDataAsString] _webkit_hasCaseInsensitivePrefix:@"about:"] || [self _web_isEmpty]; +} + +- (NSURL *)_web_URLWithLowercasedScheme +{ + CFRange range; + CFURLGetByteRangeForComponent((CFURLRef)self, kCFURLComponentScheme, &range); + if (range.location == kCFNotFound) { + return self; + } + + UInt8 static_buffer[URL_BYTES_BUFFER_LENGTH]; + UInt8 *buffer = static_buffer; + CFIndex bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, URL_BYTES_BUFFER_LENGTH); + if (bytesFilled == -1) { + CFIndex bytesToAllocate = CFURLGetBytes((CFURLRef)self, NULL, 0); + buffer = static_cast<UInt8 *>(malloc(bytesToAllocate)); + bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, bytesToAllocate); + ASSERT(bytesFilled == bytesToAllocate); + } + + int i; + BOOL changed = NO; + for (i = 0; i < range.length; ++i) { + char c = buffer[range.location + i]; + char lower = toASCIILower(c); + if (c != lower) { + buffer[range.location + i] = lower; + changed = YES; + } + } + + NSURL *result = changed + ? (NSURL *)WebCFAutorelease(CFURLCreateAbsoluteURLWithBytes(NULL, buffer, bytesFilled, kCFStringEncodingUTF8, nil, YES)) + : (NSURL *)self; + + if (buffer != static_buffer) { + free(buffer); + } + + return result; +} + + +-(BOOL)_web_hasQuestionMarkOnlyQueryString +{ + CFRange rangeWithSeparators; + CFURLGetByteRangeForComponent((CFURLRef)self, kCFURLComponentQuery, &rangeWithSeparators); + if (rangeWithSeparators.location != kCFNotFound && rangeWithSeparators.length == 1) { + return YES; + } + return NO; +} + +-(NSData *)_web_schemeSeparatorWithoutColon +{ + NSData *result = nil; + CFRange rangeWithSeparators; + CFRange range = CFURLGetByteRangeForComponent((CFURLRef)self, kCFURLComponentScheme, &rangeWithSeparators); + if (rangeWithSeparators.location != kCFNotFound) { + NSString *absoluteString = [self absoluteString]; + NSRange separatorsRange = NSMakeRange(range.location + range.length + 1, rangeWithSeparators.length - range.length - 1); + if (separatorsRange.location + separatorsRange.length <= [absoluteString length]) { + NSString *slashes = [absoluteString substringWithRange:separatorsRange]; + result = [slashes dataUsingEncoding:NSISOLatin1StringEncoding]; + } + } + return result; +} + +#define completeURL (CFURLComponentType)-1 + +-(NSData *)_web_dataForURLComponentType:(CFURLComponentType)componentType +{ + static int URLComponentTypeBufferLength = 2048; + + UInt8 staticAllBytesBuffer[URLComponentTypeBufferLength]; + UInt8 *allBytesBuffer = staticAllBytesBuffer; + + CFIndex bytesFilled = CFURLGetBytes((CFURLRef)self, allBytesBuffer, URLComponentTypeBufferLength); + if (bytesFilled == -1) { + CFIndex bytesToAllocate = CFURLGetBytes((CFURLRef)self, NULL, 0); + allBytesBuffer = static_cast<UInt8 *>(malloc(bytesToAllocate)); + bytesFilled = CFURLGetBytes((CFURLRef)self, allBytesBuffer, bytesToAllocate); + } + + CFRange range; + if (componentType != completeURL) { + range = CFURLGetByteRangeForComponent((CFURLRef)self, componentType, NULL); + if (range.location == kCFNotFound) { + return nil; + } + } + else { + range.location = 0; + range.length = bytesFilled; + } + + NSData *componentData = [NSData dataWithBytes:allBytesBuffer + range.location length:range.length]; + + const unsigned char *bytes = static_cast<const unsigned char *>([componentData bytes]); + NSMutableData *resultData = [NSMutableData data]; + // NOTE: add leading '?' to query strings non-zero length query strings. + // NOTE: retain question-mark only query strings. + if (componentType == kCFURLComponentQuery) { + if (range.length > 0 || [self _web_hasQuestionMarkOnlyQueryString]) { + [resultData appendBytes:"?" length:1]; + } + } + int i; + for (i = 0; i < range.length; i++) { + unsigned char c = bytes[i]; + if (c <= 0x20 || c >= 0x7f) { + char escaped[3]; + escaped[0] = '%'; + escaped[1] = hexDigit(c >> 4); + escaped[2] = hexDigit(c & 0xf); + [resultData appendBytes:escaped length:3]; + } + else { + char b[1]; + b[0] = c; + [resultData appendBytes:b length:1]; + } + } + + if (staticAllBytesBuffer != allBytesBuffer) { + free(allBytesBuffer); + } + + return resultData; +} + +-(NSData *)_web_schemeData +{ + return [self _web_dataForURLComponentType:kCFURLComponentScheme]; +} + +-(NSData *)_web_hostData +{ + NSData *result = [self _web_dataForURLComponentType:kCFURLComponentHost]; + NSData *scheme = [self _web_schemeData]; + // Take off localhost for file + if ([scheme _web_isCaseInsensitiveEqualToCString:"file"]) { + return ([result _web_isCaseInsensitiveEqualToCString:"localhost"]) ? nil : result; + } + return result; +} + +- (NSString *)_web_hostString +{ + NSData *data = [self _web_hostData]; + if (!data) { + data = [NSData data]; + } + return [[[NSString alloc] initWithData:[self _web_hostData] encoding:NSUTF8StringEncoding] autorelease]; +} + +- (NSString *)_webkit_suggestedFilenameWithMIMEType:(NSString *)MIMEType +{ + return suggestedFilenameWithMIMEType(self, MIMEType); +} + +@end + +@implementation NSString (WebNSURLExtras) + +- (BOOL)_web_isUserVisibleURL +{ + BOOL valid = YES; + // get buffer + + char static_buffer[1024]; + const char *p; + BOOL success = CFStringGetCString((CFStringRef)self, static_buffer, 1023, kCFStringEncodingUTF8); + if (success) { + p = static_buffer; + } else { + p = [self UTF8String]; + } + + int length = strlen(p); + + // check for characters <= 0x20 or >=0x7f, %-escape sequences of %7f, and xn--, these + // are the things that will lead _web_userVisibleString to actually change things. + int i; + for (i = 0; i < length; i++) { + unsigned char c = p[i]; + // escape control characters, space, and delete + if (c <= 0x20 || c == 0x7f) { + valid = NO; + break; + } else if (c == '%' && (i + 1 < length && isHexDigit(p[i + 1])) && i + 2 < length && isHexDigit(p[i + 2])) { + unsigned char u = (hexDigitValue(p[i + 1]) << 4) | hexDigitValue(p[i + 2]); + if (u > 0x7f) { + valid = NO; + break; + } + i += 2; + } else { + // Check for "xn--" in an efficient, non-case-sensitive, way. + if (c == '-' && i >= 3 && (p[i - 3] | 0x20) == 'x' && (p[i - 2] | 0x20) == 'n' && p[i - 1] == '-') { + valid = NO; + break; + } + } + } + + return valid; +} + + +- (BOOL)_webkit_isJavaScriptURL +{ + return [self _webkit_hasCaseInsensitivePrefix:@"javascript:"]; +} + +- (BOOL)_webkit_isFileURL +{ + return [self rangeOfString:@"file:" options:(NSCaseInsensitiveSearch | NSAnchoredSearch)].location != NSNotFound; +} + +- (NSString *)_webkit_stringByReplacingValidPercentEscapes +{ + return decodeURLEscapeSequences(self); +} + +- (NSString *)_webkit_scriptIfJavaScriptURL +{ + if (![self _webkit_isJavaScriptURL]) { + return nil; + } + return [[self substringFromIndex:11] _webkit_stringByReplacingValidPercentEscapes]; +} + +- (BOOL)_webkit_isFTPDirectoryURL +{ + int length = [self length]; + if (length < 5) { // 5 is length of "ftp:/" + return NO; + } + unichar lastChar = [self characterAtIndex:length - 1]; + return lastChar == '/' && [self _webkit_hasCaseInsensitivePrefix:@"ftp:"]; +} + + +static BOOL readIDNScriptWhiteListFile(NSString *filename) +{ + if (!filename) { + return NO; + } + FILE *file = fopen([filename fileSystemRepresentation], "r"); + if (file == NULL) { + return NO; + } + + // Read a word at a time. + // Allow comments, starting with # character to the end of the line. + while (1) { + // Skip a comment if present. + int result = fscanf(file, " #%*[^\n\r]%*[\n\r]"); + if (result == EOF) { + break; + } + + // Read a script name if present. + char word[33]; + result = fscanf(file, " %32[^# \t\n\r]%*[^# \t\n\r] ", word); + if (result == EOF) { + break; + } + if (result == 1) { + // Got a word, map to script code and put it into the array. + int32_t script = u_getPropertyValueEnum(UCHAR_SCRIPT, word); + if (script >= 0 && script < USCRIPT_CODE_LIMIT) { + size_t index = script / 32; + uint32_t mask = 1 << (script % 32); + IDNScriptWhiteList[index] |= mask; + } + } + } + fclose(file); + return YES; +} + +static void readIDNScriptWhiteList(void) +{ + // Read white list from library. + NSArray *dirs = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSAllDomainsMask, YES); + int i, numDirs = [dirs count]; + for (i = 0; i < numDirs; i++) { + NSString *dir = [dirs objectAtIndex:i]; + if (readIDNScriptWhiteListFile([dir stringByAppendingPathComponent:@"IDNScriptWhiteList.txt"])) { + return; + } + } + + // Fall back on white list inside bundle. + NSBundle *bundle = [NSBundle bundleWithIdentifier:@"com.apple.WebKit"]; + readIDNScriptWhiteListFile([bundle pathForResource:@"IDNScriptWhiteList" ofType:@"txt"]); +} + +static BOOL allCharactersInIDNScriptWhiteList(const UChar *buffer, int32_t length) +{ + pthread_once(&IDNScriptWhiteListFileRead, readIDNScriptWhiteList); + + int32_t i = 0; + while (i < length) { + UChar32 c; + U16_NEXT(buffer, i, length, c) + UErrorCode error = U_ZERO_ERROR; + UScriptCode script = uscript_getScript(c, &error); + if (error != U_ZERO_ERROR) { + LOG_ERROR("got ICU error while trying to look at scripts: %d", error); + return NO; + } + if (script < 0) { + LOG_ERROR("got negative number for script code from ICU: %d", script); + return NO; + } + if (script >= USCRIPT_CODE_LIMIT) { + return NO; + } + size_t index = script / 32; + uint32_t mask = 1 << (script % 32); + if (!(IDNScriptWhiteList[index] & mask)) { + return NO; + } + + if (isLookalikeCharacter(c)) + return NO; + } + return YES; +} + +// Return value of nil means no mapping is necessary. +// If makeString is NO, then return value is either nil or self to indicate mapping is necessary. +// If makeString is YES, then return value is either nil or the mapped string. +- (NSString *)_web_mapHostNameWithRange:(NSRange)range encode:(BOOL)encode makeString:(BOOL)makeString +{ + if (range.length > HOST_NAME_BUFFER_LENGTH) { + return nil; + } + + if ([self length] == 0) + return nil; + + UChar sourceBuffer[HOST_NAME_BUFFER_LENGTH]; + UChar destinationBuffer[HOST_NAME_BUFFER_LENGTH]; + + NSString *string = self; + if (encode && [self rangeOfString:@"%" options:NSLiteralSearch range:range].location != NSNotFound) { + NSString *substring = [self substringWithRange:range]; + substring = WebCFAutorelease(CFURLCreateStringByReplacingPercentEscapes(NULL, (CFStringRef)substring, CFSTR(""))); + if (substring != nil) { + string = substring; + range = NSMakeRange(0, [string length]); + } + } + + int length = range.length; + [string getCharacters:sourceBuffer range:range]; + + UErrorCode error = U_ZERO_ERROR; + int32_t numCharactersConverted = (encode ? uidna_IDNToASCII : uidna_IDNToUnicode) + (sourceBuffer, length, destinationBuffer, HOST_NAME_BUFFER_LENGTH, UIDNA_ALLOW_UNASSIGNED, NULL, &error); + if (error != U_ZERO_ERROR) { + return nil; + } + if (numCharactersConverted == length && memcmp(sourceBuffer, destinationBuffer, length * sizeof(UChar)) == 0) { + return nil; + } + if (!encode && !allCharactersInIDNScriptWhiteList(destinationBuffer, numCharactersConverted)) { + return nil; + } + return makeString ? (NSString *)[NSString stringWithCharacters:destinationBuffer length:numCharactersConverted] : (NSString *)self; +} + +- (BOOL)_web_hostNameNeedsDecodingWithRange:(NSRange)range +{ + return [self _web_mapHostNameWithRange:range encode:NO makeString:NO] != nil; +} + +- (BOOL)_web_hostNameNeedsEncodingWithRange:(NSRange)range +{ + return [self _web_mapHostNameWithRange:range encode:YES makeString:NO] != nil; +} + +- (NSString *)_web_decodeHostNameWithRange:(NSRange)range +{ + return [self _web_mapHostNameWithRange:range encode:NO makeString:YES]; +} + +- (NSString *)_web_encodeHostNameWithRange:(NSRange)range +{ + return [self _web_mapHostNameWithRange:range encode:YES makeString:YES]; +} + +- (NSString *)_web_decodeHostName +{ + NSString *name = [self _web_mapHostNameWithRange:NSMakeRange(0, [self length]) encode:NO makeString:YES]; + return name == nil ? self : name; +} + +- (NSString *)_web_encodeHostName +{ + NSString *name = [self _web_mapHostNameWithRange:NSMakeRange(0, [self length]) encode:YES makeString:YES]; + return name == nil ? self : name; +} + +-(NSRange)_webkit_rangeOfURLScheme +{ + NSRange colon = [self rangeOfString:@":"]; + if (colon.location != NSNotFound && colon.location > 0) { + NSRange scheme = {0, colon.location}; + static NSCharacterSet *InverseSchemeCharacterSet = nil; + if (!InverseSchemeCharacterSet) { + /* + This stuff is very expensive. 10-15 msec on a 2x1.2GHz. If not cached it swamps + everything else when adding items to the autocomplete DB. Makes me wonder if we + even need to enforce the character set here. + */ + NSString *acceptableCharacters = @"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+.-"; + InverseSchemeCharacterSet = [[[NSCharacterSet characterSetWithCharactersInString:acceptableCharacters] invertedSet] retain]; + } + NSRange illegals = [self rangeOfCharacterFromSet:InverseSchemeCharacterSet options:0 range:scheme]; + if (illegals.location == NSNotFound) + return scheme; + } + return NSMakeRange(NSNotFound, 0); +} + +-(BOOL)_webkit_looksLikeAbsoluteURL +{ + // Trim whitespace because _web_URLWithString allows whitespace. + return [[self _webkit_stringByTrimmingWhitespace] _webkit_rangeOfURLScheme].location != NSNotFound; +} + +- (NSString *)_webkit_URLFragment +{ + NSRange fragmentRange; + + fragmentRange = [self rangeOfString:@"#" options:NSLiteralSearch]; + if (fragmentRange.location == NSNotFound) + return nil; + return [self substringFromIndex:fragmentRange.location + 1]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSURLRequestExtras.h b/WebKit/mac/Misc/WebNSURLRequestExtras.h new file mode 100644 index 0000000..5dc30a2 --- /dev/null +++ b/WebKit/mac/Misc/WebNSURLRequestExtras.h @@ -0,0 +1,44 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@interface NSURLRequest (WebNSURLRequestExtras) + +- (NSString *)_web_HTTPReferrer; +- (NSString *)_web_HTTPContentType; +- (BOOL)_web_isConditionalRequest; +@end + +@interface NSMutableURLRequest (WebNSURLRequestExtras) + +- (void)_web_setHTTPContentType:(NSString *)contentType; +- (void)_web_setHTTPReferrer:(NSString *)theReferrer; +- (void)_web_setHTTPUserAgent:(NSString *)theUserAgent; + +@end diff --git a/WebKit/mac/Misc/WebNSURLRequestExtras.m b/WebKit/mac/Misc/WebNSURLRequestExtras.m new file mode 100644 index 0000000..770ff8f --- /dev/null +++ b/WebKit/mac/Misc/WebNSURLRequestExtras.m @@ -0,0 +1,88 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSURLRequestExtras.h" + +#import "WebNSURLExtras.h" + +#define WebContentType (@"Content-Type") +#define WebUserAgent (@"User-Agent") +#define WebReferrer (@"Referer") + +@implementation NSURLRequest (WebNSURLRequestExtras) + +- (NSString *)_web_HTTPReferrer +{ + return [self valueForHTTPHeaderField:WebReferrer]; +} + +- (NSString *)_web_HTTPContentType +{ + return [self valueForHTTPHeaderField:WebContentType]; +} + +- (BOOL)_web_isConditionalRequest +{ + if ([self valueForHTTPHeaderField:@"If-Match"] || + [self valueForHTTPHeaderField:@"If-Modified-Since"] || + [self valueForHTTPHeaderField:@"If-None-Match"] || + [self valueForHTTPHeaderField:@"If-Range"] || + [self valueForHTTPHeaderField:@"If-Unmodified-Since"]) + return YES; + return NO; +} + +@end + +@implementation NSMutableURLRequest (WebNSURLRequestExtras) + +- (void)_web_setHTTPContentType:(NSString *)contentType +{ + [self setValue:contentType forHTTPHeaderField:WebContentType]; +} + +- (void)_web_setHTTPReferrer:(NSString *)referrer +{ + // Do not set the referrer to a string that refers to a file URL. + // That is a potential security hole. + if ([referrer _webkit_isFileURL]) + return; + + // Don't allow empty Referer: headers; some servers refuse them + if ([referrer length] == 0) + return; + + [self setValue:referrer forHTTPHeaderField:WebReferrer]; +} + +- (void)_web_setHTTPUserAgent:(NSString *)userAgent +{ + [self setValue:userAgent forHTTPHeaderField:WebUserAgent]; +} + +@end diff --git a/WebKit/mac/Misc/WebNSUserDefaultsExtras.h b/WebKit/mac/Misc/WebNSUserDefaultsExtras.h new file mode 100644 index 0000000..487fbc0 --- /dev/null +++ b/WebKit/mac/Misc/WebNSUserDefaultsExtras.h @@ -0,0 +1,33 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@interface NSUserDefaults (WebNSUserDefaultsExtras) ++ (NSString *)_webkit_preferredLanguageCode; +@end diff --git a/WebKit/mac/Misc/WebNSUserDefaultsExtras.m b/WebKit/mac/Misc/WebNSUserDefaultsExtras.m new file mode 100644 index 0000000..383d202 --- /dev/null +++ b/WebKit/mac/Misc/WebNSUserDefaultsExtras.m @@ -0,0 +1,131 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSUserDefaultsExtras.h" + +#import "WebNSObjectExtras.h" +#import <WebKitSystemInterface.h> +#import <wtf/Assertions.h> + +@implementation NSString (WebNSUserDefaultsPrivate) + +- (NSString *)_webkit_HTTPStyleLanguageCode +{ + // Look up the language code using CFBundle. + NSString *languageCode = self; + NSString *preferredLanguageCode = WebCFAutorelease(WKCopyCFLocalizationPreferredName((CFStringRef)self)); + + if (preferredLanguageCode) + languageCode = preferredLanguageCode; + + // Make the string lowercase. + NSString *lowercaseLanguageCode = [languageCode lowercaseString]; + + // Turn a '_' into a '-' if it appears after a 2-letter language code. + if ([lowercaseLanguageCode length] < 3 || [lowercaseLanguageCode characterAtIndex:2] != '_') { + return lowercaseLanguageCode; + } + NSMutableString *result = [lowercaseLanguageCode mutableCopy]; + [result replaceCharactersInRange:NSMakeRange(2, 1) withString:@"-"]; + return [result autorelease]; +} + +@end + +@implementation NSUserDefaults (WebNSUserDefaultsExtras) + +static NSString *preferredLanguageCode = nil; +static NSLock *preferredLanguageLock = nil; +static pthread_once_t preferredLanguageLockOnce = PTHREAD_ONCE_INIT; +static pthread_once_t addDefaultsChangeObserverOnce = PTHREAD_ONCE_INIT; + +static void makeLock(void) +{ + preferredLanguageLock = [[NSLock alloc] init]; +} + ++ (void)_webkit_ensureAndLockPreferredLanguageLock +{ + pthread_once(&preferredLanguageLockOnce, makeLock); + [preferredLanguageLock lock]; +} + ++ (void)_webkit_defaultsDidChange +{ + [self _webkit_ensureAndLockPreferredLanguageLock]; + + [preferredLanguageCode release]; + preferredLanguageCode = nil; + + [preferredLanguageLock unlock]; +} + +static void addDefaultsChangeObserver(void) +{ + [[NSNotificationCenter defaultCenter] addObserver:[NSUserDefaults class] + selector:@selector(_webkit_defaultsDidChange) + name:NSUserDefaultsDidChangeNotification + object:[NSUserDefaults standardUserDefaults]]; +} + ++ (void)_webkit_addDefaultsChangeObserver +{ + pthread_once(&addDefaultsChangeObserverOnce, addDefaultsChangeObserver); +} + ++ (NSString *)_webkit_preferredLanguageCode +{ + // Get this outside the lock since it might block on the defaults lock, while we are inside registerDefaults:. + NSUserDefaults *standardDefaults = [self standardUserDefaults]; + + BOOL addObserver = NO; + + [self _webkit_ensureAndLockPreferredLanguageLock]; + + if (!preferredLanguageCode) { + NSArray *languages = [standardDefaults stringArrayForKey:@"AppleLanguages"]; + if ([languages count] == 0) { + preferredLanguageCode = [@"en" retain]; + } else { + preferredLanguageCode = [[[languages objectAtIndex:0] _webkit_HTTPStyleLanguageCode] copy]; + } + addObserver = YES; + } + + NSString *code = [[preferredLanguageCode retain] autorelease]; + + [preferredLanguageLock unlock]; + + if (addObserver) { + [self _webkit_addDefaultsChangeObserver]; + } + + return code; +} + +@end diff --git a/WebKit/mac/Misc/WebNSViewExtras.h b/WebKit/mac/Misc/WebNSViewExtras.h new file mode 100644 index 0000000..a9c2717 --- /dev/null +++ b/WebKit/mac/Misc/WebNSViewExtras.h @@ -0,0 +1,73 @@ +/* + * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <AppKit/AppKit.h> + +#define WebDragImageAlpha 0.75f + +@class DOMElement; +@class WebFrameView; +@class WebView; + +@interface NSView (WebExtras) + +// Returns the nearest enclosing view of the given class, or nil if none. +- (NSView *)_web_superviewOfClass:(Class)viewClass; +- (WebFrameView *)_web_parentWebFrameView; +- (WebView *)_webView; + +// returns whether a drag should begin starting with mouseDownEvent; if the time +// passes expiration or the mouse moves less than the hysteresis before the mouseUp event, +// returns NO, else returns YES. +- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent + withExpiration:(NSDate *)expiration + xHysteresis:(float)xHysteresis + yHysteresis:(float)yHysteresis; + +// Calls _web_dragShouldBeginFromMouseDown:withExpiration:xHysteresis:yHysteresis: with +// the default values for xHysteresis and yHysteresis +- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent + withExpiration:(NSDate *)expiration; + +// Convenience method. Returns NSDragOperationCopy if _web_bestURLFromPasteboard doesn't return nil. +// Returns NSDragOperationNone otherwise. +- (NSDragOperation)_web_dragOperationForDraggingInfo:(id <NSDraggingInfo>)sender; + +// Resizes and applies alpha to image and drags it. +- (void)_web_DragImageForElement:(DOMElement *)element + rect:(NSRect)rect + event:(NSEvent *)event + pasteboard:(NSPasteboard *)pasteboard + source:(id)source + offset:(NSPoint *)dragImageOffset; + +- (BOOL)_web_firstResponderIsSelfOrDescendantView; + +- (NSRect)_web_convertRect:(NSRect)aRect toView:(NSView *)aView; + +@end diff --git a/WebKit/mac/Misc/WebNSViewExtras.m b/WebKit/mac/Misc/WebNSViewExtras.m new file mode 100644 index 0000000..70ff68a --- /dev/null +++ b/WebKit/mac/Misc/WebNSViewExtras.m @@ -0,0 +1,243 @@ +/* + * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <WebKit/WebNSViewExtras.h> + +#import <WebKit/DOMExtensions.h> +#import <WebKit/WebDataSource.h> +#import <WebKit/WebFramePrivate.h> +#import <WebKit/WebFrameViewInternal.h> +#import <WebKit/WebNSImageExtras.h> +#import <WebKit/WebNSPasteboardExtras.h> +#import <WebKit/WebNSURLExtras.h> +#import <WebKit/WebView.h> + +#define WebDragStartHysteresisX 5.0f +#define WebDragStartHysteresisY 5.0f +#define WebMaxDragImageSize NSMakeSize(400.0f, 400.0f) +#define WebMaxOriginalImageArea (1500.0f * 1500.0f) +#define WebDragIconRightInset 7.0f +#define WebDragIconBottomInset 3.0f + +@implementation NSView (WebExtras) + +- (NSView *)_web_superviewOfClass:(Class)class +{ + NSView *view = [self superview]; + while (view && ![view isKindOfClass:class]) + view = [view superview]; + return view; +} + +- (WebFrameView *)_web_parentWebFrameView +{ + return (WebFrameView *)[self _web_superviewOfClass:[WebFrameView class]]; +} + +// FIXME: Mail is the only client of _webView, remove this method once no versions of Mail need it. +- (WebView *)_webView +{ + return (WebView *)[self _web_superviewOfClass:[WebView class]]; +} + +/* Determine whether a mouse down should turn into a drag; started as copy of NSTableView code */ +- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent + withExpiration:(NSDate *)expiration + xHysteresis:(float)xHysteresis + yHysteresis:(float)yHysteresis +{ + NSEvent *nextEvent, *firstEvent, *dragEvent, *mouseUp; + BOOL dragIt; + + if ([mouseDownEvent type] != NSLeftMouseDown) { + return NO; + } + + nextEvent = nil; + firstEvent = nil; + dragEvent = nil; + mouseUp = nil; + dragIt = NO; + + while ((nextEvent = [[self window] nextEventMatchingMask:(NSLeftMouseUpMask | NSLeftMouseDraggedMask) + untilDate:expiration + inMode:NSEventTrackingRunLoopMode + dequeue:YES]) != nil) { + if (firstEvent == nil) { + firstEvent = nextEvent; + } + + if ([nextEvent type] == NSLeftMouseDragged) { + float deltax = ABS([nextEvent locationInWindow].x - [mouseDownEvent locationInWindow].x); + float deltay = ABS([nextEvent locationInWindow].y - [mouseDownEvent locationInWindow].y); + dragEvent = nextEvent; + + if (deltax >= xHysteresis) { + dragIt = YES; + break; + } + + if (deltay >= yHysteresis) { + dragIt = YES; + break; + } + } else if ([nextEvent type] == NSLeftMouseUp) { + mouseUp = nextEvent; + break; + } + } + + // Since we've been dequeuing the events (If we don't, we'll never see the mouse up...), + // we need to push some of the events back on. It makes sense to put the first and last + // drag events and the mouse up if there was one. + if (mouseUp != nil) { + [NSApp postEvent:mouseUp atStart:YES]; + } + if (dragEvent != nil) { + [NSApp postEvent:dragEvent atStart:YES]; + } + if (firstEvent != mouseUp && firstEvent != dragEvent) { + [NSApp postEvent:firstEvent atStart:YES]; + } + + return dragIt; +} + +- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent + withExpiration:(NSDate *)expiration +{ + return [self _web_dragShouldBeginFromMouseDown:mouseDownEvent + withExpiration:expiration + xHysteresis:WebDragStartHysteresisX + yHysteresis:WebDragStartHysteresisY]; +} + + +- (NSDragOperation)_web_dragOperationForDraggingInfo:(id <NSDraggingInfo>)sender +{ + if (![NSApp modalWindow] && + ![[self window] attachedSheet] && + [sender draggingSource] != self && + [[sender draggingPasteboard] _web_bestURL]) { + + return NSDragOperationCopy; + } + + return NSDragOperationNone; +} + +- (void)_web_DragImageForElement:(DOMElement *)element + rect:(NSRect)rect + event:(NSEvent *)event + pasteboard:(NSPasteboard *)pasteboard + source:(id)source + offset:(NSPoint *)dragImageOffset +{ + NSPoint mouseDownPoint = [self convertPoint:[event locationInWindow] fromView:nil]; + NSImage *dragImage; + NSPoint origin; + + NSImage *image = [element image]; + if (image != nil && [image size].height * [image size].width <= WebMaxOriginalImageArea) { + NSSize originalSize = rect.size; + origin = rect.origin; + + dragImage = [[image copy] autorelease]; + [dragImage setScalesWhenResized:YES]; + [dragImage setSize:originalSize]; + + [dragImage _web_scaleToMaxSize:WebMaxDragImageSize]; + NSSize newSize = [dragImage size]; + + [dragImage _web_dissolveToFraction:WebDragImageAlpha]; + + // Properly orient the drag image and orient it differently if it's smaller than the original + origin.x = mouseDownPoint.x - (((mouseDownPoint.x - origin.x) / originalSize.width) * newSize.width); + origin.y = origin.y + originalSize.height; + origin.y = mouseDownPoint.y - (((mouseDownPoint.y - origin.y) / originalSize.height) * newSize.height); + } else { + // FIXME: This has been broken for a while. + // There's no way to get the MIME type for the image from a DOM element. + // The old code used WKGetPreferredExtensionForMIMEType([image MIMEType]); + NSString *extension = @""; + dragImage = [[NSWorkspace sharedWorkspace] iconForFileType:extension]; + NSSize offset = NSMakeSize([dragImage size].width - WebDragIconRightInset, -WebDragIconBottomInset); + origin = NSMakePoint(mouseDownPoint.x - offset.width, mouseDownPoint.y - offset.height); + } + + // This is the offset from the lower left corner of the image to the mouse location. Because we + // are a flipped view the calculation of Y is inverted. + if (dragImageOffset) { + dragImageOffset->x = mouseDownPoint.x - origin.x; + dragImageOffset->y = origin.y - mouseDownPoint.y; + } + + // Per kwebster, offset arg is ignored + [self dragImage:dragImage at:origin offset:NSZeroSize event:event pasteboard:pasteboard source:source slideBack:YES]; +} + +- (BOOL)_web_firstResponderIsSelfOrDescendantView +{ + NSResponder *responder = [[self window] firstResponder]; + return (responder && + (responder == self || + ([responder isKindOfClass:[NSView class]] && [(NSView *)responder isDescendantOf:self]))); +} + +- (NSRect)_web_convertRect:(NSRect)aRect toView:(NSView *)aView +{ + // Converting to this view's window; let -convertRect:toView: handle it + if (aView == nil) + return [self convertRect:aRect toView:nil]; + + // This view must be in a window. Do whatever weird thing -convertRect:toView: does in this situation. + NSWindow *thisWindow = [self window]; + if (!thisWindow) + return [self convertRect:aRect toView:aView]; + + // The other view must be in a window, too. + NSWindow *otherWindow = [aView window]; + if (!otherWindow) + return [self convertRect:aRect toView:aView]; + + // Convert to this window's coordinates + NSRect convertedRect = [self convertRect:aRect toView:nil]; + + // Convert to screen coordinates + convertedRect.origin = [thisWindow convertBaseToScreen:convertedRect.origin]; + + // Convert to other window's coordinates + convertedRect.origin = [otherWindow convertScreenToBase:convertedRect.origin]; + + // Convert to other view's coordinates + convertedRect = [aView convertRect:convertedRect fromView:nil]; + + return convertedRect; +} + +@end diff --git a/WebKit/mac/Misc/WebNSWindowExtras.h b/WebKit/mac/Misc/WebNSWindowExtras.h new file mode 100644 index 0000000..0aebd4f --- /dev/null +++ b/WebKit/mac/Misc/WebNSWindowExtras.h @@ -0,0 +1,34 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Cocoa/Cocoa.h> + +@interface NSWindow (WebExtras) +// centers "visually", putting 1/3 of the remaining space above, and 2/3 below +- (void)centerOverMainWindow; +@end diff --git a/WebKit/mac/Misc/WebNSWindowExtras.m b/WebKit/mac/Misc/WebNSWindowExtras.m new file mode 100644 index 0000000..ef27b13 --- /dev/null +++ b/WebKit/mac/Misc/WebNSWindowExtras.m @@ -0,0 +1,52 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebNSWindowExtras.h" + +@implementation NSWindow (WebExtras) + +- (void)centerOverMainWindow +{ + NSRect frameToCenterOver; + if ([NSApp mainWindow]) { + frameToCenterOver = [[NSApp mainWindow] frame]; + } else { + frameToCenterOver = [[NSScreen mainScreen] visibleFrame]; + } + + NSSize size = [self frame].size; + NSPoint origin; + origin.y = NSMaxY(frameToCenterOver) + - (frameToCenterOver.size.height - size.height) / 3 + - size.height; + origin.x = frameToCenterOver.origin.x + + (frameToCenterOver.size.width - size.width) / 2; + [self setFrameOrigin:origin]; +} + +@end diff --git a/WebKit/mac/Misc/WebStringTruncator.h b/WebKit/mac/Misc/WebStringTruncator.h new file mode 100644 index 0000000..ed00d27 --- /dev/null +++ b/WebKit/mac/Misc/WebStringTruncator.h @@ -0,0 +1,44 @@ +/* + * Copyright (C) 2005 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import <Foundation/Foundation.h> + +@class NSFont; + +@interface WebStringTruncator : NSObject + ++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font; + +// Default font is [NSFont menuFontOfSize:0]. ++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth; + ++ (NSString *)rightTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font; + ++ (float)widthOfString:(NSString *)string font:(NSFont *)font; + +@end diff --git a/WebKit/mac/Misc/WebStringTruncator.m b/WebKit/mac/Misc/WebStringTruncator.m new file mode 100644 index 0000000..c395e7a --- /dev/null +++ b/WebKit/mac/Misc/WebStringTruncator.m @@ -0,0 +1,92 @@ +/* + * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#import "WebStringTruncator.h" + +#import "WebSystemInterface.h" +#import <WebCore/Font.h> +#import <WebCore/FontPlatformData.h> +#import <WebCore/PlatformString.h> +#import <WebCore/StringTruncator.h> + +using namespace WebCore; + +static NSFont *defaultMenuFont() +{ + static NSFont *defaultMenuFont = nil; + if (!defaultMenuFont) { + defaultMenuFont = [NSFont menuFontOfSize:0]; + CFRetain(defaultMenuFont); + } + return defaultMenuFont; +} + +static Font& fontFromNSFont(NSFont *font) +{ + static NSFont *currentFont; + static Font currentRenderer; + + if ([font isEqual:currentFont]) + return currentRenderer; + if (currentFont) + CFRelease(currentFont); + currentFont = font; + CFRetain(currentFont); + FontPlatformData f(font); + currentRenderer = Font(f, ![[NSGraphicsContext currentContext] isDrawingToScreen]); + return currentRenderer; +} + +@implementation WebStringTruncator + ++ (void)initialize +{ + InitWebCoreSystemInterface(); +} + ++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth +{ + return StringTruncator::centerTruncate(string, maxWidth, fontFromNSFont(defaultMenuFont())); +} + ++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font +{ + return StringTruncator::centerTruncate(string, maxWidth, fontFromNSFont(font)); +} + ++ (NSString *)rightTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font +{ + return StringTruncator::rightTruncate(string, maxWidth, fontFromNSFont(font)); +} + ++ (float)widthOfString:(NSString *)string font:(NSFont *)font +{ + return StringTruncator::width(string, fontFromNSFont(font)); +} + +@end diff --git a/WebKit/mac/Misc/WebTypesInternal.h b/WebKit/mac/Misc/WebTypesInternal.h new file mode 100644 index 0000000..4b97ab3 --- /dev/null +++ b/WebKit/mac/Misc/WebTypesInternal.h @@ -0,0 +1,34 @@ +/* + * Copyright (C) 2006, 2007 Apple Inc. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifdef BUILDING_ON_TIGER +typedef int NSInteger; +typedef unsigned int NSUInteger; +#endif + + |