WebCore:

        Reviewed by Darin.

        Changed the blocked exception log message to match AppKit's blocked exception message.

        * platform/mac/BlockExceptions.mm:
        (ReportBlockedObjCException):

WebKit:

        Reviewed by Darin.

        <rdar://problem/5443883> Uncaught Objective-C exceptions in WebKit clients lead to hard-to-diagnose crashes

        Changed all the direct delegate calls to use helper functions that have direct access to
        WebView's delegate objects. These helper methods will catch any ObjC exceptions and call
        ReportDiscardedDelegateException to log the discarded exception. WebView's that have
        catchesDelegateExceptions set to NO will not pay the cost of a @try/@catch. The delegate
        forwarders also have the same behavior.

        * Misc/WebKitLogging.h:
        * Misc/WebKitLogging.m:
        (ReportDiscardedDelegateException):
        * Plugins/WebBaseNetscapePluginView.mm:
        (-[WebBaseNetscapePluginView loadPluginRequest:]):
        * Plugins/WebNullPluginView.mm:
        (-[WebNullPluginView viewDidMoveToWindow]):
        * WebCoreSupport/WebChromeClient.mm:
        (WebChromeClient::createWindow):
        (WebChromeClient::createModalDialog):
        (WebChromeClient::runModal):
        (WebChromeClient::toolbarsVisible):
        (WebChromeClient::statusbarVisible):
        (WebChromeClient::addMessageToConsole):
        (WebChromeClient::canRunBeforeUnloadConfirmPanel):
        (WebChromeClient::runBeforeUnloadConfirmPanel):
        (WebChromeClient::runJavaScriptAlert):
        (WebChromeClient::runJavaScriptConfirm):
        (WebChromeClient::runJavaScriptPrompt):
        (WebChromeClient::shouldInterruptJavaScript):
        (WebChromeClient::setStatusbarText):
        (WebChromeClient::print):
        * WebCoreSupport/WebContextMenuClient.mm:
        (WebContextMenuClient::getCustomMenuFromDefaultItems):
        (WebContextMenuClient::contextMenuItemSelected):
        * WebCoreSupport/WebDragClient.mm:
        (WebDragClient::startDrag):
        * WebCoreSupport/WebEditorClient.mm:
        (WebEditorClient::textFieldDidBeginEditing):
        (WebEditorClient::textFieldDidEndEditing):
        (WebEditorClient::textDidChangeInTextField):
        (WebEditorClient::doTextFieldCommandFromEvent):
        (WebEditorClient::textWillBeDeletedInTextField):
        (WebEditorClient::textDidChangeInTextArea):
        * WebCoreSupport/WebFrameBridge.mm:
        (-[WebFrameBridge viewForPluginWithFrame:URL:attributeNames:attributeValues:MIMEType:DOMElement:loadManually:]):
        * WebCoreSupport/WebFrameLoaderClient.mm:
        (WebFrameLoaderClient::dispatchDidLoadResourceFromMemoryCache):
        (WebFrameLoaderClient::assignIdentifierToInitialRequest):
        (WebFrameLoaderClient::dispatchWillSendRequest):
        (WebFrameLoaderClient::dispatchDidReceiveAuthenticationChallenge):
        (WebFrameLoaderClient::dispatchDidCancelAuthenticationChallenge):
        (WebFrameLoaderClient::dispatchDidReceiveResponse):
        (WebFrameLoaderClient::willCacheResponse):
        (WebFrameLoaderClient::dispatchDidReceiveContentLength):
        (WebFrameLoaderClient::dispatchDidFinishLoading):
        (WebFrameLoaderClient::dispatchDidFailLoading):
        (WebFrameLoaderClient::dispatchDidHandleOnloadEvents):
        (WebFrameLoaderClient::dispatchDidReceiveServerRedirectForProvisionalLoad):
        (WebFrameLoaderClient::dispatchDidCancelClientRedirect):
        (WebFrameLoaderClient::dispatchWillPerformClientRedirect):
        (WebFrameLoaderClient::dispatchDidChangeLocationWithinPage):
        (WebFrameLoaderClient::dispatchWillClose):
        (WebFrameLoaderClient::dispatchDidReceiveIcon):
        (WebFrameLoaderClient::dispatchDidStartProvisionalLoad):
        (WebFrameLoaderClient::dispatchDidReceiveTitle):
        (WebFrameLoaderClient::dispatchDidCommitLoad):
        (WebFrameLoaderClient::dispatchDidFailProvisionalLoad):
        (WebFrameLoaderClient::dispatchDidFailLoad):
        (WebFrameLoaderClient::dispatchDidFinishDocumentLoad):
        (WebFrameLoaderClient::dispatchDidFinishLoad):
        (WebFrameLoaderClient::dispatchDidFirstLayout):
        (WebFrameLoaderClient::dispatchCreatePage):
        (WebFrameLoaderClient::dispatchUnableToImplementPolicy):
        (WebFrameLoaderClient::dispatchWillSubmitForm):
        (WebFrameLoaderClient::dispatchDidLoadMainResource):
        * WebView/WebHTMLView.mm:
        (-[WebHTMLView callDelegateDoCommandBySelectorIfNeeded:]):
        (-[WebHTMLView validateUserInterfaceItem:]):
        * WebView/WebPDFView.mm:
        (-[WebPDFView validateUserInterfaceItem:]):
        (-[WebPDFView PDFViewSavePDFToDownloadFolder:]):
        * WebView/WebView.mm:
        (-[WebView _openNewWindowWithRequest:]):
        (-[WebView _menuForElement:defaultItems:]):
        (-[WebView _mouseDidMoveOverElement:modifierFlags:]):
        (-[WebView _cacheResourceLoadDelegateImplementations]):
        (-[WebView _cacheFrameLoadDelegateImplementations]):
        (-[WebView _policyDelegateForwarder]):
        (-[WebView _UIDelegateForwarder]):
        (-[WebView _editingDelegateForwarder]):
        (-[WebView _scriptDebugDelegateForwarder]):
        (-[WebView _setCatchesDelegateExceptions:]):
        (-[WebView _catchesDelegateExceptions]):
        (-[_WebSafeForwarder initWithTarget:defaultTarget:]):
        (-[_WebSafeForwarder forwardInvocation:]):
        (-[_WebSafeForwarder methodSignatureForSelector:]):
        (-[WebView _commonInitializationWithFrameName:groupName:]):
        (-[WebView validateUserInterfaceItem:]):
        (-[WebView _headerHeight]):
        (-[WebView _footerHeight]):
        (-[WebView _drawHeaderInRect:]):
        (-[WebView _drawFooterInRect:]):
        (-[WebView _shouldChangeSelectedDOMRange:toDOMRange:affinity:stillSelecting:]):
        (CallDelegate):
        (CallDelegateReturningFloat):
        (CallDelegateReturningBoolean):
        (CallUIDelegate):
        (CallUIDelegateReturningFloat):
        (CallUIDelegateReturningBoolean):
        (CallFrameLoadDelegate):
        (CallResourceLoadDelegate):
        (CallFormDelegate):
        (CallFormDelegateReturningBoolean):
        * WebView/WebViewInternal.h:
        * WebView/WebViewPrivate.h:



git-svn-id: http://svn.webkit.org/repository/webkit/trunk@25396 268f45cc-cd09-0410-ab3c-d52691b4dbfc
diff --git a/WebCore/ChangeLog b/WebCore/ChangeLog
index e5e8efc..244145c 100644
--- a/WebCore/ChangeLog
+++ b/WebCore/ChangeLog
@@ -1,3 +1,12 @@
+2007-09-05  Timothy Hatcher  <timothy@apple.com>
+
+        Reviewed by Darin.
+
+        Changed the blocked exception log message to match AppKit's blocked exception message.
+
+        * platform/mac/BlockExceptions.mm:
+        (ReportBlockedObjCException):
+
 2007-09-06  Darin Adler  <darin@apple.com>
 
         Reviewed by Hyatt.
diff --git a/WebCore/platform/mac/BlockExceptions.mm b/WebCore/platform/mac/BlockExceptions.mm
index 0ce50d7..f2dc1ec 100644
--- a/WebCore/platform/mac/BlockExceptions.mm
+++ b/WebCore/platform/mac/BlockExceptions.mm
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2003 Apple Computer, Inc.  All rights reserved.
+ * Copyright (C) 2003, 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
@@ -28,11 +28,11 @@
 
 #import <wtf/Assertions.h>
 
-void ReportBlockedObjCException(NSException *localException)
+void ReportBlockedObjCException(NSException *exception)
 {
 #if ASSERT_DISABLED
-    NSLog(@"Uncaught exception - %@\n", localException);
+    NSLog(@"*** WebKit discarding exception: <%@> %@", [exception name], [exception reason]);
 #else
-    ASSERT_WITH_MESSAGE(0, "Uncaught exception - %@", localException);
+    ASSERT_WITH_MESSAGE(0, "Uncaught exception - %@", exception);
 #endif
 }
diff --git a/WebKit/ChangeLog b/WebKit/ChangeLog
index ef7c73b..3dd2ad8 100644
--- a/WebKit/ChangeLog
+++ b/WebKit/ChangeLog
@@ -1,3 +1,122 @@
+2007-09-05  Timothy Hatcher  <timothy@apple.com>
+
+        Reviewed by Darin.
+
+        <rdar://problem/5443883> Uncaught Objective-C exceptions in WebKit clients lead to hard-to-diagnose crashes
+
+        Changed all the direct delegate calls to use helper functions that have direct access to
+        WebView's delegate objects. These helper methods will catch any ObjC exceptions and call
+        ReportDiscardedDelegateException to log the discarded exception. WebView's that have
+        catchesDelegateExceptions set to NO will not pay the cost of a @try/@catch. The delegate
+        forwarders also have the same behavior.
+
+        * Misc/WebKitLogging.h:
+        * Misc/WebKitLogging.m:
+        (ReportDiscardedDelegateException):
+        * Plugins/WebBaseNetscapePluginView.mm:
+        (-[WebBaseNetscapePluginView loadPluginRequest:]):
+        * Plugins/WebNullPluginView.mm:
+        (-[WebNullPluginView viewDidMoveToWindow]):
+        * WebCoreSupport/WebChromeClient.mm:
+        (WebChromeClient::createWindow):
+        (WebChromeClient::createModalDialog):
+        (WebChromeClient::runModal):
+        (WebChromeClient::toolbarsVisible):
+        (WebChromeClient::statusbarVisible):
+        (WebChromeClient::addMessageToConsole):
+        (WebChromeClient::canRunBeforeUnloadConfirmPanel):
+        (WebChromeClient::runBeforeUnloadConfirmPanel):
+        (WebChromeClient::runJavaScriptAlert):
+        (WebChromeClient::runJavaScriptConfirm):
+        (WebChromeClient::runJavaScriptPrompt):
+        (WebChromeClient::shouldInterruptJavaScript):
+        (WebChromeClient::setStatusbarText):
+        (WebChromeClient::print):
+        * WebCoreSupport/WebContextMenuClient.mm:
+        (WebContextMenuClient::getCustomMenuFromDefaultItems):
+        (WebContextMenuClient::contextMenuItemSelected):
+        * WebCoreSupport/WebDragClient.mm:
+        (WebDragClient::startDrag):
+        * WebCoreSupport/WebEditorClient.mm:
+        (WebEditorClient::textFieldDidBeginEditing):
+        (WebEditorClient::textFieldDidEndEditing):
+        (WebEditorClient::textDidChangeInTextField):
+        (WebEditorClient::doTextFieldCommandFromEvent):
+        (WebEditorClient::textWillBeDeletedInTextField):
+        (WebEditorClient::textDidChangeInTextArea):
+        * WebCoreSupport/WebFrameBridge.mm:
+        (-[WebFrameBridge viewForPluginWithFrame:URL:attributeNames:attributeValues:MIMEType:DOMElement:loadManually:]):
+        * WebCoreSupport/WebFrameLoaderClient.mm:
+        (WebFrameLoaderClient::dispatchDidLoadResourceFromMemoryCache):
+        (WebFrameLoaderClient::assignIdentifierToInitialRequest):
+        (WebFrameLoaderClient::dispatchWillSendRequest):
+        (WebFrameLoaderClient::dispatchDidReceiveAuthenticationChallenge):
+        (WebFrameLoaderClient::dispatchDidCancelAuthenticationChallenge):
+        (WebFrameLoaderClient::dispatchDidReceiveResponse):
+        (WebFrameLoaderClient::willCacheResponse):
+        (WebFrameLoaderClient::dispatchDidReceiveContentLength):
+        (WebFrameLoaderClient::dispatchDidFinishLoading):
+        (WebFrameLoaderClient::dispatchDidFailLoading):
+        (WebFrameLoaderClient::dispatchDidHandleOnloadEvents):
+        (WebFrameLoaderClient::dispatchDidReceiveServerRedirectForProvisionalLoad):
+        (WebFrameLoaderClient::dispatchDidCancelClientRedirect):
+        (WebFrameLoaderClient::dispatchWillPerformClientRedirect):
+        (WebFrameLoaderClient::dispatchDidChangeLocationWithinPage):
+        (WebFrameLoaderClient::dispatchWillClose):
+        (WebFrameLoaderClient::dispatchDidReceiveIcon):
+        (WebFrameLoaderClient::dispatchDidStartProvisionalLoad):
+        (WebFrameLoaderClient::dispatchDidReceiveTitle):
+        (WebFrameLoaderClient::dispatchDidCommitLoad):
+        (WebFrameLoaderClient::dispatchDidFailProvisionalLoad):
+        (WebFrameLoaderClient::dispatchDidFailLoad):
+        (WebFrameLoaderClient::dispatchDidFinishDocumentLoad):
+        (WebFrameLoaderClient::dispatchDidFinishLoad):
+        (WebFrameLoaderClient::dispatchDidFirstLayout):
+        (WebFrameLoaderClient::dispatchCreatePage):
+        (WebFrameLoaderClient::dispatchUnableToImplementPolicy):
+        (WebFrameLoaderClient::dispatchWillSubmitForm):
+        (WebFrameLoaderClient::dispatchDidLoadMainResource):
+        * WebView/WebHTMLView.mm:
+        (-[WebHTMLView callDelegateDoCommandBySelectorIfNeeded:]):
+        (-[WebHTMLView validateUserInterfaceItem:]):
+        * WebView/WebPDFView.mm:
+        (-[WebPDFView validateUserInterfaceItem:]):
+        (-[WebPDFView PDFViewSavePDFToDownloadFolder:]):
+        * WebView/WebView.mm:
+        (-[WebView _openNewWindowWithRequest:]):
+        (-[WebView _menuForElement:defaultItems:]):
+        (-[WebView _mouseDidMoveOverElement:modifierFlags:]):
+        (-[WebView _cacheResourceLoadDelegateImplementations]):
+        (-[WebView _cacheFrameLoadDelegateImplementations]):
+        (-[WebView _policyDelegateForwarder]):
+        (-[WebView _UIDelegateForwarder]):
+        (-[WebView _editingDelegateForwarder]):
+        (-[WebView _scriptDebugDelegateForwarder]):
+        (-[WebView _setCatchesDelegateExceptions:]):
+        (-[WebView _catchesDelegateExceptions]):
+        (-[_WebSafeForwarder initWithTarget:defaultTarget:]):
+        (-[_WebSafeForwarder forwardInvocation:]):
+        (-[_WebSafeForwarder methodSignatureForSelector:]):
+        (-[WebView _commonInitializationWithFrameName:groupName:]):
+        (-[WebView validateUserInterfaceItem:]):
+        (-[WebView _headerHeight]):
+        (-[WebView _footerHeight]):
+        (-[WebView _drawHeaderInRect:]):
+        (-[WebView _drawFooterInRect:]):
+        (-[WebView _shouldChangeSelectedDOMRange:toDOMRange:affinity:stillSelecting:]):
+        (CallDelegate):
+        (CallDelegateReturningFloat):
+        (CallDelegateReturningBoolean):
+        (CallUIDelegate):
+        (CallUIDelegateReturningFloat):
+        (CallUIDelegateReturningBoolean):
+        (CallFrameLoadDelegate):
+        (CallResourceLoadDelegate):
+        (CallFormDelegate):
+        (CallFormDelegateReturningBoolean):
+        * WebView/WebViewInternal.h:
+        * WebView/WebViewPrivate.h:
+
 2007-09-04  Timothy Hatcher  <timothy@apple.com>
 
         Reviewed by Darin.
diff --git a/WebKit/Misc/WebKitLogging.h b/WebKit/Misc/WebKitLogging.h
index edaaa5a..0bf791c 100644
--- a/WebKit/Misc/WebKitLogging.h
+++ b/WebKit/Misc/WebKitLogging.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2005 Apple Computer, Inc.  All rights reserved.
+ * 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
@@ -78,6 +78,7 @@
 #define ASSERT_MAIN_THREAD() ((void)0)
 #endif
 
+void ReportDiscardedDelegateException(SEL delegateSelector, id exception);
 
 #ifdef __cplusplus
 }
diff --git a/WebKit/Misc/WebKitLogging.m b/WebKit/Misc/WebKitLogging.m
index fbac3fa..4e4294f 100644
--- a/WebKit/Misc/WebKitLogging.m
+++ b/WebKit/Misc/WebKitLogging.m
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2005 Apple Computer, Inc.  All rights reserved.
+ * 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
@@ -103,3 +103,13 @@
 {
     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/Plugins/WebBaseNetscapePluginView.mm b/WebKit/Plugins/WebBaseNetscapePluginView.mm
index b2c9702..fbacc62 100644
--- a/WebKit/Plugins/WebBaseNetscapePluginView.mm
+++ b/WebKit/Plugins/WebBaseNetscapePluginView.mm
@@ -2106,15 +2106,9 @@
         frame = [[self webFrame] findFrameNamed:frameName];
     
         if (frame == nil) {
-            WebView *newWebView = nil;
             WebView *currentWebView = [self webView];
-            id wd = [currentWebView UIDelegate];
-            if ([wd respondsToSelector:@selector(webView:createWebViewWithRequest:)]) {
-                newWebView = [wd webView:currentWebView createWebViewWithRequest:nil];
-            } else {
-                newWebView = [[WebDefaultUIDelegate sharedUIDelegate] webView:currentWebView createWebViewWithRequest:nil];
-            }
-            
+            WebView *newWebView = CallUIDelegate(currentWebView, @selector(webView:createWebViewWithRequest:), nil);
+
             if (!newWebView) {
                 if ([pluginRequest sendNotification]) {
                     [self willCallPlugInFunction];
diff --git a/WebKit/Plugins/WebNullPluginView.mm b/WebKit/Plugins/WebNullPluginView.mm
index 1184035..2e7d372 100644
--- a/WebKit/Plugins/WebNullPluginView.mm
+++ b/WebKit/Plugins/WebNullPluginView.mm
@@ -71,15 +71,15 @@
 
 - (void)viewDidMoveToWindow
 {
-    if(!didSendError && _window && error){
+    if (!didSendError && _window && error) {
         didSendError = YES;
         WebFrame *webFrame = kit(core(element)->document()->frame());
         WebView *webView = [webFrame webView];
         WebDataSource *dataSource = [webFrame _dataSource];
 
-        id resourceLoadDelegate = [webView resourceLoadDelegate];
-        if ([resourceLoadDelegate respondsToSelector:@selector(webView:plugInFailedWithError:dataSource:)])
-            [resourceLoadDelegate webView:webView plugInFailedWithError:error dataSource:dataSource];
+        WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+        if (implementations.plugInFailedWithErrorFunc)
+            CallResourceLoadDelegate(implementations.plugInFailedWithErrorFunc, webView, @selector(webView:plugInFailedWithError:dataSource:), error, dataSource);
     }
 }
 
diff --git a/WebKit/WebCoreSupport/WebChromeClient.mm b/WebKit/WebCoreSupport/WebChromeClient.mm
index 4f337e5..d78c9d9 100644
--- a/WebKit/WebCoreSupport/WebChromeClient.mm
+++ b/WebKit/WebCoreSupport/WebChromeClient.mm
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2006, 2007 Apple Inc.  All rights reserved.
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
  * Copyright (C) 2007 Trolltech ASA
  *
  * Redistribution and use in source and binary forms, with or without
@@ -136,14 +136,7 @@
     NSURLRequest *URLRequest = nil;
     if (!request.isEmpty())
         URLRequest = request.resourceRequest().nsURLRequest();
-
-    WebView *newWebView;
-    id delegate = [m_webView UIDelegate];
-    if ([delegate respondsToSelector:@selector(webView:createWebViewWithRequest:)])
-        newWebView = [delegate webView:m_webView createWebViewWithRequest:URLRequest];
-    else
-        newWebView = [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView createWebViewWithRequest:URLRequest];
-
+    WebView *newWebView = CallUIDelegate(m_webView, @selector(webView:createWebViewWithRequest:), URLRequest);
     return core(newWebView);
 }
 
@@ -156,12 +149,9 @@
     WebView *newWebView = nil;
     id delegate = [m_webView UIDelegate];
     if ([delegate respondsToSelector:@selector(webView:createWebViewModalDialogWithRequest:)])
-        newWebView = [delegate webView:m_webView createWebViewModalDialogWithRequest:URLRequest];
+        newWebView = CallUIDelegate(m_webView, @selector(webView:createWebViewModalDialogWithRequest:), URLRequest);
     else if ([delegate respondsToSelector:@selector(webView:createWebViewWithRequest:)])
-        newWebView = [delegate webView:m_webView createWebViewWithRequest:URLRequest];
-    else
-        newWebView = [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView createWebViewWithRequest:URLRequest];
-
+        newWebView = CallUIDelegate(m_webView, @selector(webView:createWebViewWithRequest:), URLRequest);
     return core(newWebView);
 }
 
@@ -177,7 +167,7 @@
 
 void WebChromeClient::runModal()
 {
-    [[m_webView UIDelegate] webViewRunModal:m_webView];
+    CallUIDelegate(m_webView, @selector(webViewRunModal:));
 }
 
 void WebChromeClient::setToolbarsVisible(bool b)
@@ -187,10 +177,7 @@
 
 bool WebChromeClient::toolbarsVisible()
 {
-    id delegate = [m_webView UIDelegate];
-    if ([delegate respondsToSelector:@selector(webViewAreToolbarsVisible:)])
-        return [delegate webViewAreToolbarsVisible:m_webView];
-    return [[WebDefaultUIDelegate sharedUIDelegate] webViewAreToolbarsVisible:m_webView];
+    return CallUIDelegateReturningBoolean(NO, m_webView, @selector(webViewAreToolbarsVisible:));
 }
 
 void WebChromeClient::setStatusbarVisible(bool b)
@@ -200,13 +187,9 @@
 
 bool WebChromeClient::statusbarVisible()
 {
-    id delegate = [m_webView UIDelegate];
-    if ([delegate respondsToSelector:@selector(webViewIsStatusBarVisible:)])
-        return [delegate webViewIsStatusBarVisible:m_webView];
-    return [[WebDefaultUIDelegate sharedUIDelegate] webViewIsStatusBarVisible:m_webView];
+    return CallUIDelegateReturningBoolean(NO, m_webView, @selector(webViewIsStatusBarVisible:));
 }
 
-
 void WebChromeClient::setScrollbarsVisible(bool b)
 {
     [[[m_webView mainFrame] frameView] setAllowsScrolling:b];
@@ -236,30 +219,28 @@
 
 void WebChromeClient::addMessageToConsole(const String& message, unsigned int lineNumber, const String& sourceURL)
 {
-    id wd = [m_webView UIDelegate];
-    if ([wd respondsToSelector:@selector(webView:addMessageToConsole:)]) {
-        NSDictionary *dictionary = [NSDictionary dictionaryWithObjectsAndKeys:
-            (NSString *)message, @"message",
-            [NSNumber numberWithInt: lineNumber], @"lineNumber",
-            (NSString *)sourceURL, @"sourceURL",
-            NULL];
-        
-        [wd webView:m_webView addMessageToConsole:dictionary];
-    }    
+    id delegate = [m_webView UIDelegate];
+    SEL selector = @selector(webView:addMessageToConsole:);
+    if (![delegate respondsToSelector:selector])
+        return;
+
+    NSDictionary *dictionary = [[NSDictionary alloc] initWithObjectsAndKeys:
+        (NSString *)message, @"message", [NSNumber numberWithUnsignedInt:lineNumber], @"lineNumber",
+        (NSString *)sourceURL, @"sourceURL", NULL];
+
+    CallUIDelegate(m_webView, selector, dictionary);
+
+    [dictionary release];
 }
 
 bool WebChromeClient::canRunBeforeUnloadConfirmPanel()
 {
-    id wd = [m_webView UIDelegate];
-    return [wd respondsToSelector:@selector(webView:runBeforeUnloadConfirmPanelWithMessage:initiatedByFrame:)];
+    return [[m_webView UIDelegate] respondsToSelector:@selector(webView:runBeforeUnloadConfirmPanelWithMessage:initiatedByFrame:)];
 }
 
 bool WebChromeClient::runBeforeUnloadConfirmPanel(const String& message, Frame* frame)
 {
-    id wd = [m_webView UIDelegate];
-    if ([wd respondsToSelector:@selector(webView:runBeforeUnloadConfirmPanelWithMessage:initiatedByFrame:)])
-        return [wd webView:m_webView runBeforeUnloadConfirmPanelWithMessage:message initiatedByFrame:kit(frame)];
-    return true;
+    return CallUIDelegateReturningBoolean(true, m_webView, @selector(webView:runBeforeUnloadConfirmPanelWithMessage:initiatedByFrame:), message, kit(frame));
 }
 
 void WebChromeClient::closeWindowSoon()
@@ -284,69 +265,68 @@
 
 void WebChromeClient::runJavaScriptAlert(Frame* frame, const String& message)
 {
-    id wd = [m_webView UIDelegate];
-    // Check whether delegate implements new version, then whether delegate implements old version. If neither,
-    // fall back to shared delegate's implementation of new version.
-    if ([wd respondsToSelector:@selector(webView:runJavaScriptAlertPanelWithMessage:initiatedByFrame:)])
-        [wd webView:m_webView runJavaScriptAlertPanelWithMessage:message initiatedByFrame:kit(frame)];
-    else if ([wd respondsToSelector:@selector(webView:runJavaScriptAlertPanelWithMessage:)])
-        [wd webView:m_webView runJavaScriptAlertPanelWithMessage:message];
-    else
-        [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView runJavaScriptAlertPanelWithMessage:message initiatedByFrame:kit(frame)];    
+    id delegate = [m_webView UIDelegate];
+    SEL selector = @selector(webView:runJavaScriptAlertPanelWithMessage:initiatedByFrame:);
+    if ([delegate respondsToSelector:selector]) {
+        CallUIDelegate(m_webView, selector, message, kit(frame));
+        return;
+    }
+
+    // Call the old version of the delegate method if it is implemented.
+    selector = @selector(webView:runJavaScriptAlertPanelWithMessage:);
+    if ([delegate respondsToSelector:selector]) {
+        CallUIDelegate(m_webView, selector, message);
+        return;
+    }
 }
 
 bool WebChromeClient::runJavaScriptConfirm(Frame* frame, const String& message)
 {
-    id wd = [m_webView UIDelegate];
-    // Check whether delegate implements new version, then whether delegate implements old version. If neither,
-    // fall back to shared delegate's implementation of new version.
-    if ([wd respondsToSelector:@selector(webView:runJavaScriptConfirmPanelWithMessage:initiatedByFrame:)])
-        return [wd webView:m_webView runJavaScriptConfirmPanelWithMessage:message initiatedByFrame:kit(frame)];
-    if ([wd respondsToSelector:@selector(webView:runJavaScriptConfirmPanelWithMessage:)])
-        return [wd webView:m_webView runJavaScriptConfirmPanelWithMessage:message];    
-    return [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView runJavaScriptConfirmPanelWithMessage:message initiatedByFrame:kit(frame)];
+    id delegate = [m_webView UIDelegate];
+    SEL selector = @selector(webView:runJavaScriptConfirmPanelWithMessage:initiatedByFrame:);
+    if ([delegate respondsToSelector:selector])
+        return CallUIDelegateReturningBoolean(NO, m_webView, selector, message, kit(frame));
+
+    // Call the old version of the delegate method if it is implemented.
+    selector = @selector(webView:runJavaScriptConfirmPanelWithMessage:);
+    if ([delegate respondsToSelector:selector])
+        return CallUIDelegateReturningBoolean(NO, m_webView, selector, message);
+
+    return NO;
 }
 
 bool WebChromeClient::runJavaScriptPrompt(Frame* frame, const String& prompt, const String& defaultText, String& result)
 {
-    id wd = [m_webView UIDelegate];
-    // Check whether delegate implements new version, then whether delegate implements old version. If neither,
-    // fall back to shared delegate's implementation of new version.
-    if ([wd respondsToSelector:@selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:initiatedByFrame:)])
-        result = [wd webView:m_webView runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText initiatedByFrame:kit(frame)];
-    else if ([wd respondsToSelector:@selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:)])
-        result = [wd webView:m_webView runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText];
-    else
-        result = [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText initiatedByFrame:kit(frame)];
-    
+    id delegate = [m_webView UIDelegate];
+    SEL selector = @selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:initiatedByFrame:);
+    if ([delegate respondsToSelector:selector]) {
+        result = (NSString *)CallUIDelegate(m_webView, selector, prompt, defaultText, kit(frame));
+        return !result.isNull();
+    }
+
+    // Call the old version of the delegate method if it is implemented.
+    selector = @selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:);
+    if ([delegate respondsToSelector:selector]) {
+        result = (NSString *)CallUIDelegate(m_webView, selector, prompt, defaultText);
+        return !result.isNull();
+    }
+
+    result = [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText initiatedByFrame:kit(frame)];
     return !result.isNull();
 }
 
 bool WebChromeClient::shouldInterruptJavaScript()
 {
-    BEGIN_BLOCK_OBJC_EXCEPTIONS;
-    id wd = [m_webView UIDelegate];
-    if ([wd respondsToSelector:@selector(webViewShouldInterruptJavaScript:)])
-        return [wd webViewShouldInterruptJavaScript:m_webView];
-    return false;
-    END_BLOCK_OBJC_EXCEPTIONS;
-    
-    return false;
+    return CallUIDelegate(m_webView, @selector(webViewShouldInterruptJavaScript:));
 }
 
 void WebChromeClient::setStatusbarText(const WebCore::String& status)
 {
-    id wd = [m_webView UIDelegate];
-
-    if ([wd respondsToSelector:@selector(webView:setStatusText:)]) {
-        // We want the temporaries allocated here to be released even before returning to the 
-        // event loop; see <http://bugs.webkit.org/show_bug.cgi?id=9880>.
-        NSAutoreleasePool* localPool = [[NSAutoreleasePool alloc] init];
-    
-        [wd webView:m_webView setStatusText:status];
-        
-        [localPool drain];
-    }
+    // We want the temporaries allocated here to be released even before returning to the 
+    // event loop; see <http://bugs.webkit.org/show_bug.cgi?id=9880>.
+    NSAutoreleasePool* localPool = [[NSAutoreleasePool alloc] init];
+    CallUIDelegate(m_webView, @selector(webView:setStatusText:), (NSString *)status);
+    [localPool drain];
 }
 
 bool WebChromeClient::tabsToLinks() const
@@ -386,9 +366,5 @@
 void WebChromeClient::print(Frame* frame)
 {
     WebFrameView* frameView = [kit(frame) frameView];
-    id wd = [m_webView UIDelegate];
-    if ([wd respondsToSelector:@selector(webView:printFrameView:)])
-        [wd webView:m_webView printFrameView:frameView];
-    else
-        [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView printFrameView:frameView];
+    CallUIDelegate(m_webView, @selector(webView:printFrameView:), frameView);
 }
diff --git a/WebKit/WebCoreSupport/WebContextMenuClient.mm b/WebKit/WebCoreSupport/WebContextMenuClient.mm
index a63086a..8924348 100644
--- a/WebKit/WebCoreSupport/WebContextMenuClient.mm
+++ b/WebKit/WebCoreSupport/WebContextMenuClient.mm
@@ -249,7 +249,8 @@
 NSMutableArray* WebContextMenuClient::getCustomMenuFromDefaultItems(ContextMenu* defaultMenu)
 {
     id delegate = [m_webView UIDelegate];
-    if (![delegate respondsToSelector:@selector(webView:contextMenuItemsForElement:defaultMenuItems:)])
+    SEL selector = @selector(webView:contextMenuItemsForElement:defaultMenuItems:);
+    if (![delegate respondsToSelector:selector])
         return defaultMenu->platformDescription();
 
     NSDictionary *element = [[[WebElementDictionary alloc] initWithHitTestResult:defaultMenu->hitTestResult()] autorelease];
@@ -264,25 +265,29 @@
     }
 
     NSMutableArray *defaultMenuItems = defaultMenu->platformDescription();
-    
+
     unsigned defaultItemsCount = [defaultMenuItems count];
     for (unsigned i = 0; i < defaultItemsCount; ++i)
         [[defaultMenuItems objectAtIndex:i] setRepresentedObject:element];
-            
+
     NSMutableArray *savedItems = [fixMenusToSendToOldClients(defaultMenuItems) retain];
-    NSMutableArray *newMenuItems = [[[delegate webView:m_webView contextMenuItemsForElement:element defaultMenuItems:defaultMenuItems] mutableCopy] autorelease];
+    NSArray *delegateSuppliedItems = CallUIDelegate(m_webView, selector, element, defaultMenuItems);
+    NSMutableArray *newMenuItems = [delegateSuppliedItems mutableCopy];
     fixMenusReceivedFromOldClients(newMenuItems, savedItems);
     [savedItems release];
-    return newMenuItems;
+    return [newMenuItems autorelease];
 }
 
 void WebContextMenuClient::contextMenuItemSelected(ContextMenuItem* item, const ContextMenu* parentMenu)
 {
     id delegate = [m_webView UIDelegate];
-    if ([delegate respondsToSelector:@selector(webView:contextMenuItemSelected:forElement:)]) {
+    SEL selector = @selector(webView:contextMenuItemSelected:forElement:);
+    if ([delegate respondsToSelector:selector]) {
         NSDictionary *element = [[WebElementDictionary alloc] initWithHitTestResult:parentMenu->hitTestResult()];
         NSMenuItem *platformItem = item->releasePlatformDescription();
-        [delegate webView:m_webView contextMenuItemSelected:platformItem forElement:element];
+
+        CallUIDelegate(m_webView, selector, platformItem, element);
+
         [element release];
         [platformItem release];
     }
diff --git a/WebKit/WebCoreSupport/WebDragClient.mm b/WebKit/WebCoreSupport/WebDragClient.mm
index 1e3b2fb..0dedbf1 100644
--- a/WebKit/WebCoreSupport/WebDragClient.mm
+++ b/WebKit/WebCoreSupport/WebDragClient.mm
@@ -32,6 +32,7 @@
 #import "WebFrameInternal.h"
 #import "WebHTMLViewInternal.h"
 #import "WebHTMLViewPrivate.h"
+#import "WebKitLogging.h"
 #import "WebNSPasteboardExtras.h"
 #import "WebNSURLExtras.h"
 #import "WebUIDelegate.h"
@@ -97,13 +98,21 @@
     
     [topHTMLView _stopAutoscrollTimer];
     NSPasteboard *pasteboard = static_cast<ClipboardMac*>(clipboard)->pasteboard();
-    
-    // note per kwebster, the offset arg below is always ignored in positioning the image
-    id UIDelegate = [m_webView UIDelegate];
-    if ([UIDelegate respondsToSelector:@selector(webView:dragImage:at:offset:event:pasteboard:source:slideBack:forView:)])
-        [UIDelegate webView:m_webView dragImage:dragImage.get() at:(NSPoint)at offset:NSMakeSize(0, 0) event:event pasteboard:pasteboard source:htmlView.get() slideBack:YES forView:topHTMLView];
-    else
-        [topHTMLView dragImage:dragImage.get() at:(NSPoint)at offset:NSMakeSize(0, 0) event:event pasteboard:pasteboard source:htmlView.get() slideBack:YES];
+
+    NSSize offset = {0.0, 0.0};
+    id delegate = [m_webView UIDelegate];
+    SEL selector = @selector(webView:dragImage:at:offset:event:pasteboard:source:slideBack:forView:);
+    if ([delegate respondsToSelector:selector]) {
+        if ([m_webView _catchesDelegateExceptions]) {
+            @try {
+                [delegate webView:m_webView dragImage:dragImage.get() at:at offset:offset event:event pasteboard:pasteboard source:htmlView.get() slideBack:YES forView:topHTMLView];
+            } @catch (id exception) {
+                ReportDiscardedDelegateException(selector, exception);
+            }
+        } else
+            [delegate webView:m_webView dragImage:dragImage.get() at:at offset:offset event:event pasteboard:pasteboard source:htmlView.get() slideBack:YES forView:topHTMLView];
+    } else
+        [topHTMLView dragImage:dragImage.get() at:at offset:offset event:event pasteboard:pasteboard source:htmlView.get() slideBack:YES];
 }
 
 DragImageRef WebDragClient::createDragImageForLink(KURL& url, const String& title, Frame* frame)
diff --git a/WebKit/WebCoreSupport/WebEditorClient.mm b/WebKit/WebCoreSupport/WebEditorClient.mm
index 68b8ab3..bf8b3c4 100644
--- a/WebKit/WebCoreSupport/WebEditorClient.mm
+++ b/WebKit/WebCoreSupport/WebEditorClient.mm
@@ -458,21 +458,21 @@
 {
     DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
     FormDelegateLog(inputElement);
-    [[m_webView _formDelegate] textFieldDidBeginEditing:inputElement inFrame:kit(element->document()->frame())];
+    CallFormDelegate(m_webView, @selector(textFieldDidBeginEditing:inFrame:), inputElement, kit(element->document()->frame()));
 }
 
 void WebEditorClient::textFieldDidEndEditing(Element* element)
 {
     DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
     FormDelegateLog(inputElement);
-    [[m_webView _formDelegate] textFieldDidEndEditing:inputElement inFrame:kit(element->document()->frame())];
+    CallFormDelegate(m_webView, @selector(textFieldDidEndEditing:inFrame:), inputElement, kit(element->document()->frame()));
 }
     
 void WebEditorClient::textDidChangeInTextField(Element* element)
 {
     DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
     FormDelegateLog(inputElement);
-    [[m_webView _formDelegate] textDidChangeInTextField:(DOMHTMLInputElement *)inputElement inFrame:kit(element->document()->frame())];
+    CallFormDelegate(m_webView, @selector(textDidChangeInTextField:inFrame:), inputElement, kit(element->document()->frame()));
 }
 
 static SEL selectorForKeyEvent(KeyboardEvent* event)
@@ -500,32 +500,25 @@
 bool WebEditorClient::doTextFieldCommandFromEvent(Element* element, KeyboardEvent* event)
 {
     DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
-
-    bool result = false;
     FormDelegateLog(inputElement);
-
-    SEL selector = selectorForKeyEvent(event);
-    if (selector)
-        result = [[m_webView _formDelegate] textField:inputElement doCommandBySelector:selector inFrame:kit(element->document()->frame())];
-
-    return result;
+    if (SEL commandSelector = selectorForKeyEvent(event))
+        return CallFormDelegateReturningBoolean(NO, m_webView, @selector(textField:doCommandBySelector:inFrame:), inputElement, commandSelector, kit(element->document()->frame()));
+    return NO;
 }
 
 void WebEditorClient::textWillBeDeletedInTextField(Element* element)
 {
     DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
-
-    // We're using the deleteBackward selector for all deletion operations since the autofill code treats all deletions the same way.
     FormDelegateLog(inputElement);
-    [[m_webView _formDelegate] textField:inputElement doCommandBySelector:@selector(deleteBackward:) inFrame:kit(element->document()->frame())];
+    // We're using the deleteBackward selector for all deletion operations since the autofill code treats all deletions the same way.
+    CallFormDelegateReturningBoolean(NO, m_webView, @selector(textField:doCommandBySelector:inFrame:), inputElement, @selector(deleteBackward:), kit(element->document()->frame()));
 }
 
 void WebEditorClient::textDidChangeInTextArea(Element* element)
 {
     DOMHTMLTextAreaElement* textAreaElement = [DOMHTMLTextAreaElement _wrapHTMLTextAreaElement:(HTMLTextAreaElement*)element];
-
     FormDelegateLog(textAreaElement);
-    [[m_webView _formDelegate] textDidChangeInTextArea:textAreaElement inFrame:kit(element->document()->frame())];
+    CallFormDelegate(m_webView, @selector(textDidChangeInTextArea:inFrame:), textAreaElement, kit(element->document()->frame()));
 }
 
 void WebEditorClient::ignoreWordInSpellDocument(const String& text)
diff --git a/WebKit/WebCoreSupport/WebFrameBridge.mm b/WebKit/WebCoreSupport/WebFrameBridge.mm
index bd935f2..ab63123 100644
--- a/WebKit/WebCoreSupport/WebFrameBridge.mm
+++ b/WebKit/WebCoreSupport/WebFrameBridge.mm
@@ -293,21 +293,6 @@
     return [[_frame frameView] window];
 }
 
-- (BOOL)runJavaScriptTextInputPanelWithPrompt:(NSString *)prompt defaultText:(NSString *)defaultText returningText:(NSString **)result
-{
-    WebView *wv = [self webView];
-    id wd = [wv UIDelegate];
-    // Check whether delegate implements new version, then whether delegate implements old version. If neither,
-    // fall back to shared delegate's implementation of new version.
-    if ([wd respondsToSelector:@selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:initiatedByFrame:)])
-        *result = [wd webView:wv runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText initiatedByFrame:_frame];
-    else if ([wd respondsToSelector:@selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:)])
-        *result = [wd webView:wv runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText];
-    else
-        *result = [[WebDefaultUIDelegate sharedUIDelegate] webView:wv runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText initiatedByFrame:_frame];
-    return *result != nil;
-}
-
 - (void)runOpenPanelForFileButtonWithResultListener:(id<WebCoreOpenPanelResultListener>)resultListener
 {
     WebView *wv = [self webView];
@@ -446,20 +431,24 @@
     NSView *view = nil;
     int errorCode = 0;
 
-    WebView *wv = [self webView];
-    id wd = [wv UIDelegate];
+    WebView *webView = [self webView];
+    SEL selector = @selector(webView:plugInViewWithArguments:);
 
-    if ([wd respondsToSelector:@selector(webView:plugInViewWithArguments:)]) {
+    if ([[webView UIDelegate] respondsToSelector:selector]) {
         NSMutableDictionary *attributes = [[NSMutableDictionary alloc] initWithObjects:attributeValues forKeys:attributeNames];
-        NSDictionary *arguments = [NSDictionary dictionaryWithObjectsAndKeys:
+        NSDictionary *arguments = [[NSDictionary alloc] initWithObjectsAndKeys:
             attributes, WebPlugInAttributesKey,
             [NSNumber numberWithInt:loadManually ? WebPlugInModeFull : WebPlugInModeEmbed], WebPlugInModeKey,
-            URL, WebPlugInBaseURLKey, // URL might be nil, so add it last
             [NSNumber numberWithBool:!loadManually], WebPlugInShouldLoadMainResourceKey,
             element, WebPlugInContainingElementKey,
+            URL, WebPlugInBaseURLKey, // URL might be nil, so add it last
             nil];
+
+        view = CallUIDelegate(webView, selector, arguments);
+
         [attributes release];
-        view = [wd webView:wv plugInViewWithArguments:arguments];
+        [arguments release];
+
         if (view)
             return view;
     }
@@ -726,13 +715,10 @@
 {
     WebView *webView = getWebView(_frame);
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidClearWindowObjectForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didClearWindowObjectForFrameFunc(frameLoadDelegate, @selector(webView:didClearWindowObject:forFrame:), webView, m_frame->windowScriptObject(), _frame);
-    } else if (implementations.delegateImplementsWindowScriptObjectAvailable) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.windowScriptObjectAvailableFunc(frameLoadDelegate, @selector(webView:windowScriptObjectAvailable:), webView, m_frame->windowScriptObject());
-    }
+    if (implementations.didClearWindowObjectForFrameFunc)
+        CallFrameLoadDelegate(implementations.didClearWindowObjectForFrameFunc, webView, @selector(webView:didClearWindowObject:forFrame:), m_frame->windowScriptObject(), _frame);
+    else if (implementations.windowScriptObjectAvailableFunc)
+        CallFrameLoadDelegate(implementations.windowScriptObjectAvailableFunc, webView, @selector(webView:windowScriptObjectAvailable:), m_frame->windowScriptObject());
 
     if ([webView scriptDebugDelegate] || [WebScriptDebugServer listenerCount]) {
         [_frame _detachScriptDebugger];
@@ -747,27 +733,20 @@
 
 - (void)dashboardRegionsChanged:(NSMutableDictionary *)regions
 {
-    WebView *wv = [self webView];
-    id wd = [wv UIDelegate];
-    
-    [wv _addScrollerDashboardRegions:regions];
-    
+    WebView *webView = [self webView];
+    [webView _addScrollerDashboardRegions:regions];
+
     if (![self _compareDashboardRegions:regions]) {
-        if ([wd respondsToSelector:@selector(webView:dashboardRegionsChanged:)]) {
-            [wd webView:wv dashboardRegionsChanged:regions];
-            [lastDashboardRegions release];
-            lastDashboardRegions = [regions retain];
-        }
+        CallUIDelegate(webView, @selector(webView:dashboardRegionsChanged:), regions);
+
+        [lastDashboardRegions release];
+        lastDashboardRegions = [regions retain];
     }
 }
 
 - (void)willPopupMenu:(NSMenu *)menu
 {
-    WebView *wv = [self webView];
-    id wd = [wv UIDelegate];
-        
-    if ([wd respondsToSelector:@selector(webView:willPopupMenu:)])
-        [wd webView:wv willPopupMenu:menu];
+    CallUIDelegate([self webView], @selector(webView:willPopupMenu:), menu);
 }
 
 - (NSRect)customHighlightRect:(NSString*)type forLine:(NSRect)lineRect representedNode:(WebCore::Node *)node
diff --git a/WebKit/WebCoreSupport/WebFrameLoaderClient.mm b/WebKit/WebCoreSupport/WebFrameLoaderClient.mm
index 7796e95..83edbc1 100644
--- a/WebKit/WebCoreSupport/WebFrameLoaderClient.mm
+++ b/WebKit/WebCoreSupport/WebFrameLoaderClient.mm
@@ -310,26 +310,23 @@
 bool WebFrameLoaderClient::dispatchDidLoadResourceFromMemoryCache(DocumentLoader* loader, const ResourceRequest& request, const ResourceResponse& response, int length)
 {
     WebView *webView = getWebView(m_webFrame.get());
-
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
-    if (!implementations.delegateImplementsDidLoadResourceFromMemoryCache)
+    if (!implementations.didLoadResourceFromMemoryCacheFunc)
         return false;
 
-    implementations.didLoadResourceFromMemoryCacheFunc(resourceLoadDelegate, @selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:), webView, request.nsURLRequest(), response.nsURLResponse(), length, dataSource(loader));
+    CallResourceLoadDelegate(implementations.didLoadResourceFromMemoryCacheFunc, webView, @selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:), request.nsURLRequest(), response.nsURLResponse(), length, dataSource(loader));
     return true;
 }
 
 void WebFrameLoaderClient::assignIdentifierToInitialRequest(unsigned long identifier, DocumentLoader* loader, const ResourceRequest& request)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
 
-    id object;
+    id object = nil;
     BOOL shouldRelease = NO;
-    if (implementations.delegateImplementsIdentifierForRequest)
-        object = implementations.identifierForRequestFunc(resourceLoadDelegate, @selector(webView:identifierForInitialRequest:fromDataSource:), webView, request.nsURLRequest(), dataSource(loader));
+    if (implementations.identifierForRequestFunc)
+        object = CallResourceLoadDelegate(implementations.identifierForRequestFunc, webView, @selector(webView:identifierForInitialRequest:fromDataSource:), request.nsURLRequest(), dataSource(loader));
     else {
         object = [[NSObject alloc] init];
         shouldRelease = YES;
@@ -344,27 +341,25 @@
 void WebFrameLoaderClient::dispatchWillSendRequest(DocumentLoader* loader, unsigned long identifier, ResourceRequest& request, const ResourceResponse& redirectResponse)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
 
     if (redirectResponse.isNull())
         static_cast<WebDocumentLoaderMac*>(loader)->increaseLoadCount(identifier);
 
-    if (implementations.delegateImplementsWillSendRequest)
-        request = implementations.willSendRequestFunc(resourceLoadDelegate, @selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:), webView, [webView _objectForIdentifier:identifier], request.nsURLRequest(), redirectResponse.nsURLResponse(), dataSource(loader));
+    if (implementations.willSendRequestFunc)
+        request = (NSURLRequest *)CallResourceLoadDelegate(implementations.willSendRequestFunc, webView, @selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:), [webView _objectForIdentifier:identifier], request.nsURLRequest(), redirectResponse.nsURLResponse(), dataSource(loader));
 }
 
 void WebFrameLoaderClient::dispatchDidReceiveAuthenticationChallenge(DocumentLoader* loader, unsigned long identifier, const AuthenticationChallenge& challenge)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = [webView resourceLoadDelegate];
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
 
     NSURLAuthenticationChallenge *webChallenge = mac(challenge);
 
-    if (implementations.delegateImplementsDidReceiveAuthenticationChallenge) {
+    if (implementations.didReceiveAuthenticationChallengeFunc) {
         if (id resource = [webView _objectForIdentifier:identifier]) {
-            [resourceLoadDelegate webView:webView resource:resource didReceiveAuthenticationChallenge:webChallenge fromDataSource:dataSource(loader)];
+            CallResourceLoadDelegate(implementations.didReceiveAuthenticationChallengeFunc, webView, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:), resource, webChallenge, dataSource(loader));
             return;
         }
     }
@@ -376,14 +371,12 @@
 void WebFrameLoaderClient::dispatchDidCancelAuthenticationChallenge(DocumentLoader* loader, unsigned long identifier, const AuthenticationChallenge&challenge)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = [webView resourceLoadDelegate];
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
-
     NSURLAuthenticationChallenge *webChallenge = mac(challenge);
 
-    if (implementations.delegateImplementsDidCancelAuthenticationChallenge) {
+    if (implementations.didCancelAuthenticationChallengeFunc) {
         if (id resource = [webView _objectForIdentifier:identifier]) {
-            [resourceLoadDelegate webView:webView resource:resource didCancelAuthenticationChallenge:webChallenge fromDataSource:dataSource(loader)];
+            CallResourceLoadDelegate(implementations.didCancelAuthenticationChallengeFunc, webView, @selector(webView:resource:didCancelAuthenticationChallenge:fromDataSource:), resource, webChallenge, dataSource(loader));
             return;
         }
     }
@@ -394,23 +387,21 @@
 void WebFrameLoaderClient::dispatchDidReceiveResponse(DocumentLoader* loader, unsigned long identifier, const ResourceResponse& response)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
-
-    if (implementations.delegateImplementsDidReceiveResponse) {
+    if (implementations.didReceiveResponseFunc) {
         if (id resource = [webView _objectForIdentifier:identifier])
-            implementations.didReceiveResponseFunc(resourceLoadDelegate, @selector(webView:resource:didReceiveResponse:fromDataSource:), webView, resource, response.nsURLResponse(), dataSource(loader));
+            CallResourceLoadDelegate(implementations.didReceiveResponseFunc, webView, @selector(webView:resource:didReceiveResponse:fromDataSource:), resource, response.nsURLResponse(), dataSource(loader));
     }
 }
 
 NSCachedURLResponse* WebFrameLoaderClient::willCacheResponse(DocumentLoader* loader, unsigned long identifier, NSCachedURLResponse* response) const
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsWillCacheResponse) {
-        if (id resource = [webView _objectForIdentifier:identifier]) 
-            return implementations.willCacheResponseFunc(resourceLoadDelegate, @selector(webView:resource:willCacheResponse:fromDataSource:), webView, resource, response, dataSource(loader));
+
+    if (implementations.willCacheResponseFunc) {
+        if (id resource = [webView _objectForIdentifier:identifier])
+            return CallResourceLoadDelegate(implementations.willCacheResponseFunc, webView, @selector(webView:resource:willCacheResponse:fromDataSource:), resource, response, dataSource(loader));
     }
 
     return response;
@@ -419,25 +410,23 @@
 void WebFrameLoaderClient::dispatchDidReceiveContentLength(DocumentLoader* loader, unsigned long identifier, int lengthReceived)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
-
-    if (implementations.delegateImplementsDidReceiveContentLength) {
-        if (id resource = [webView _objectForIdentifier:identifier]) 
-            implementations.didReceiveContentLengthFunc(resourceLoadDelegate, @selector(webView:resource:didReceiveContentLength:fromDataSource:), webView, resource, (NSUInteger)lengthReceived, dataSource(loader));
+    if (implementations.didReceiveContentLengthFunc) {
+        if (id resource = [webView _objectForIdentifier:identifier])
+            CallResourceLoadDelegate(implementations.didReceiveContentLengthFunc, webView, @selector(webView:resource:didReceiveContentLength:fromDataSource:), resource, (NSInteger)lengthReceived, dataSource(loader));
     }
 }
 
 void WebFrameLoaderClient::dispatchDidFinishLoading(DocumentLoader* loader, unsigned long identifier)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
 
-    if (implementations.delegateImplementsDidFinishLoadingFromDataSource) {
+    if (implementations.didFinishLoadingFromDataSourceFunc) {
         if (id resource = [webView _objectForIdentifier:identifier])
-            implementations.didFinishLoadingFromDataSourceFunc(resourceLoadDelegate, @selector(webView:resource:didFinishLoadingFromDataSource:), webView, resource, dataSource(loader));
+            CallResourceLoadDelegate(implementations.didFinishLoadingFromDataSourceFunc, webView, @selector(webView:resource:didFinishLoadingFromDataSource:), resource, dataSource(loader));
     }
+
     [webView _removeObjectForIdentifier:identifier];
 
     static_cast<WebDocumentLoaderMac*>(loader)->decreaseLoadCount(identifier);
@@ -446,13 +435,13 @@
 void WebFrameLoaderClient::dispatchDidFailLoading(DocumentLoader* loader, unsigned long identifier, const ResourceError& error)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    id resourceLoadDelegate = WebViewGetResourceLoadDelegate(webView);
     WebResourceDelegateImplementationCache implementations = WebViewGetResourceLoadDelegateImplementations(webView);
 
-    if (implementations.delegateImplementsDidFailLoadingWithErrorFromDataSource) {
+    if (implementations.didFailLoadingWithErrorFromDataSourceFunc) {
         if (id resource = [webView _objectForIdentifier:identifier])
-            implementations.didFailLoadingWithErrorFromDataSourceFunc(resourceLoadDelegate, @selector(webView:resource:didFailLoadingWithError:fromDataSource:), webView, resource, error, dataSource(loader));
+            CallResourceLoadDelegate(implementations.didFailLoadingWithErrorFromDataSourceFunc, webView, @selector(webView:resource:didFailLoadingWithError:fromDataSource:), resource, (NSError *)error, dataSource(loader));
     }
+
     [webView _removeObjectForIdentifier:identifier];
 
     static_cast<WebDocumentLoaderMac*>(loader)->decreaseLoadCount(identifier);
@@ -462,60 +451,48 @@
 {
     WebView *webView = getWebView(m_webFrame.get());
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidHandleOnloadEventsForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didHandleOnloadEventsForFrameFunc(frameLoadDelegate, @selector(webView:didHandleOnloadEventsForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didHandleOnloadEventsForFrameFunc)
+        CallFrameLoadDelegate(implementations.didHandleOnloadEventsForFrameFunc, webView, @selector(webView:didHandleOnloadEventsForFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidReceiveServerRedirectForProvisionalLoad()
 {
     WebView *webView = getWebView(m_webFrame.get());
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidReceiveServerRedirectForProvisionalLoadForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didReceiveServerRedirectForProvisionalLoadForFrameFunc(frameLoadDelegate, @selector(webView:didReceiveServerRedirectForProvisionalLoadForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didReceiveServerRedirectForProvisionalLoadForFrameFunc)
+        CallFrameLoadDelegate(implementations.didReceiveServerRedirectForProvisionalLoadForFrameFunc, webView, @selector(webView:didHandleOnloadEventsForFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidCancelClientRedirect()
 {
     WebView *webView = getWebView(m_webFrame.get());
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidCancelClientRedirectForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didCancelClientRedirectForFrameFunc(frameLoadDelegate, @selector(webView:didCancelClientRedirectForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didCancelClientRedirectForFrameFunc)
+        CallFrameLoadDelegate(implementations.didCancelClientRedirectForFrameFunc, webView, @selector(webView:didCancelClientRedirectForFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchWillPerformClientRedirect(const KURL& URL, double delay, double fireDate)
 {
     WebView *webView = getWebView(m_webFrame.get());
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsWillPerformClientRedirectToURLDelayFireDateForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.willPerformClientRedirectToURLDelayFireDateForFrameFunc(frameLoadDelegate, @selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:), webView, URL.getNSURL(), delay, [NSDate dateWithTimeIntervalSince1970:fireDate], m_webFrame.get());
-    }
+    if (implementations.willPerformClientRedirectToURLDelayFireDateForFrameFunc)
+        CallFrameLoadDelegate(implementations.willPerformClientRedirectToURLDelayFireDateForFrameFunc, webView, @selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:), URL.getNSURL(), delay, [NSDate dateWithTimeIntervalSince1970:fireDate], m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidChangeLocationWithinPage()
 {
     WebView *webView = getWebView(m_webFrame.get());
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidChangeLocationWithinPageForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didChangeLocationWithinPageForFrameFunc(frameLoadDelegate, @selector(webView:didChangeLocationWithinPageForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didChangeLocationWithinPageForFrameFunc)
+        CallFrameLoadDelegate(implementations.didChangeLocationWithinPageForFrameFunc, webView, @selector(webView:didChangeLocationWithinPageForFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchWillClose()
 {
     WebView *webView = getWebView(m_webFrame.get());   
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsWillCloseFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.willCloseFrameFunc(frameLoadDelegate, @selector(webView:willCloseFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.willCloseFrameFunc)
+        CallFrameLoadDelegate(implementations.willCloseFrameFunc, webView, @selector(webView:willCloseFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidReceiveIcon()
@@ -527,12 +504,10 @@
     [webView _willChangeValueForKey:_WebMainFrameIconKey];
 
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidReceiveIconForFrame) {
+    if (implementations.didReceiveIconForFrameFunc) {
         Image* image = iconDatabase()->iconForPageURL(core(m_webFrame.get())->loader()->url().url(), IntSize(16, 16));
-        if (NSImage *icon = webGetNSImage(image, NSMakeSize(16, 16))) {
-            id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-            implementations.didReceiveIconForFrameFunc(frameLoadDelegate, @selector(webView:didReceiveIcon:forFrame:), webView, icon, m_webFrame.get());
-        }
+        if (NSImage *icon = webGetNSImage(image, NSMakeSize(16, 16)))
+            CallFrameLoadDelegate(implementations.didReceiveIconForFrameFunc, webView, @selector(webView:didReceiveIcon:forFrame:), icon, m_webFrame.get());
     }
 
     [webView _didChangeValueForKey:_WebMainFrameIconKey];
@@ -544,20 +519,16 @@
     [webView _didStartProvisionalLoadForFrame:m_webFrame.get()];
 
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidStartProvisionalLoadForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didStartProvisionalLoadForFrameFunc(frameLoadDelegate, @selector(webView:didStartProvisionalLoadForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didStartProvisionalLoadForFrameFunc)
+        CallFrameLoadDelegate(implementations.didStartProvisionalLoadForFrameFunc, webView, @selector(webView:didStartProvisionalLoadForFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidReceiveTitle(const String& title)
 {
     WebView *webView = getWebView(m_webFrame.get());   
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidReceiveTitleForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didReceiveTitleForFrameFunc(frameLoadDelegate, @selector(webView:didReceiveTitle:forFrame:), webView, title, m_webFrame.get());
-    }
+    if (implementations.didReceiveTitleForFrameFunc)
+        CallFrameLoadDelegate(implementations.didReceiveTitleForFrameFunc, webView, @selector(webView:didReceiveTitle:forFrame:), (NSString *)title, m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidCommitLoad()
@@ -569,21 +540,19 @@
     [webView _didCommitLoadForFrame:m_webFrame.get()];
 
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidCommitLoadForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didCommitLoadForFrameFunc(frameLoadDelegate, @selector(webView:didCommitLoadForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didCommitLoadForFrameFunc)
+        CallFrameLoadDelegate(implementations.didCommitLoadForFrameFunc, webView, @selector(webView:didCommitLoadForFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidFailProvisionalLoad(const ResourceError& error)
 {
     WebView *webView = getWebView(m_webFrame.get());   
     [webView _didFailProvisionalLoadWithError:error forFrame:m_webFrame.get()];
+
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidFailProvisionalLoadWithErrorForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didFailProvisionalLoadWithErrorForFrameFunc(frameLoadDelegate, @selector(webView:didFailProvisionalLoadWithError:forFrame:), webView, error, m_webFrame.get());
-    }
+    if (implementations.didFailProvisionalLoadWithErrorForFrameFunc)
+        CallFrameLoadDelegate(implementations.didFailProvisionalLoadWithErrorForFrameFunc, webView, @selector(webView:didFailProvisionalLoadWithError:forFrame:), (NSError *)error, m_webFrame.get());
+
     [m_webFrame->_private->internalLoadDelegate webFrame:m_webFrame.get() didFinishLoadWithError:error];
 }
 
@@ -593,10 +562,8 @@
     [webView _didFailLoadWithError:error forFrame:m_webFrame.get()];
 
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidFailLoadWithErrorForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didFailLoadWithErrorForFrameFunc(frameLoadDelegate, @selector(webView:didFailLoadWithError:forFrame:), webView, error, m_webFrame.get());
-    }
+    if (implementations.didFailLoadWithErrorForFrameFunc)
+        CallFrameLoadDelegate(implementations.didFailLoadWithErrorForFrameFunc, webView, @selector(webView:didFailLoadWithError:forFrame:), (NSError *)error, m_webFrame.get());
 
     [m_webFrame->_private->internalLoadDelegate webFrame:m_webFrame.get() didFinishLoadWithError:error];
 }
@@ -605,10 +572,8 @@
 {
     WebView *webView = getWebView(m_webFrame.get());
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidFinishDocumentLoadForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didFinishDocumentLoadForFrameFunc(frameLoadDelegate, @selector(webView:didFinishDocumentLoadForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didFinishDocumentLoadForFrameFunc)
+        CallFrameLoadDelegate(implementations.didFinishDocumentLoadForFrameFunc, webView, @selector(webView:didFinishDocumentLoadForFrame:), m_webFrame.get());
 }
 
 void WebFrameLoaderClient::dispatchDidFinishLoad()
@@ -617,10 +582,8 @@
     [webView _didFinishLoadForFrame:m_webFrame.get()];
 
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidFinishLoadForFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didFinishLoadForFrameFunc(frameLoadDelegate, @selector(webView:didFinishLoadForFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didFinishLoadForFrameFunc)
+        CallFrameLoadDelegate(implementations.didFinishLoadForFrameFunc, webView, @selector(webView:didFinishLoadForFrame:), m_webFrame.get());
 
     [m_webFrame->_private->internalLoadDelegate webFrame:m_webFrame.get() didFinishLoadWithError:nil];
 }
@@ -629,19 +592,15 @@
 {
     WebView *webView = getWebView(m_webFrame.get());
     WebFrameLoadDelegateImplementationCache implementations = WebViewGetFrameLoadDelegateImplementations(webView);
-    if (implementations.delegateImplementsDidFirstLayoutInFrame) {
-        id frameLoadDelegate = WebViewGetFrameLoadDelegate(webView);
-        implementations.didFirstLayoutInFrameFunc(frameLoadDelegate, @selector(webView:didFirstLayoutInFrame:), webView, m_webFrame.get());
-    }
+    if (implementations.didFirstLayoutInFrameFunc)
+        CallFrameLoadDelegate(implementations.didFirstLayoutInFrameFunc, webView, @selector(webView:didFirstLayoutInFrame:), m_webFrame.get());
 }
 
 Frame* WebFrameLoaderClient::dispatchCreatePage()
 {
     WebView *currentWebView = getWebView(m_webFrame.get());
-    id wd = [currentWebView UIDelegate];
-    if ([wd respondsToSelector:@selector(webView:createWebViewWithRequest:)])
-        return core([[wd webView:currentWebView createWebViewWithRequest:nil] mainFrame]);
-    return 0;
+    WebView *newWebView = CallUIDelegate(currentWebView, @selector(webView:createWebViewWithRequest:), nil);
+    return core([newWebView mainFrame]);
 }
 
 void WebFrameLoaderClient::dispatchShow()
@@ -694,8 +653,7 @@
 void WebFrameLoaderClient::dispatchUnableToImplementPolicy(const ResourceError& error)
 {
     WebView *webView = getWebView(m_webFrame.get());
-    [[webView _policyDelegateForwarder] webView:webView
-        unableToImplementPolicyWithError:error frame:m_webFrame.get()];    
+    [[webView _policyDelegateForwarder] webView:webView unableToImplementPolicyWithError:error frame:m_webFrame.get()];    
 }
 
 void WebFrameLoaderClient::dispatchWillSubmitForm(FramePolicyFunction function, PassRefPtr<FormState> formState)
@@ -711,11 +669,7 @@
     for (HashMap<String, String>::const_iterator it = formState->values().begin(); it != end; ++it)
         [dictionary setObject:it->second forKey:it->first];
 
-    [formDelegate frame:m_webFrame.get()
-            sourceFrame:kit(formState->sourceFrame())
-         willSubmitForm:kit(formState->form())
-             withValues:dictionary
-     submissionListener:setUpPolicyListener(function).get()];
+    CallFormDelegate(getWebView(m_webFrame.get()), @selector(frame:sourceFrame:willSubmitForm:withValues:submissionListener:), m_webFrame.get(), kit(formState->sourceFrame()), kit(formState->form()), dictionary, setUpPolicyListener(function).get());
 
     [dictionary release];
 }
@@ -723,8 +677,7 @@
 void WebFrameLoaderClient::dispatchDidLoadMainResource(DocumentLoader* loader)
 {
     if ([WebScriptDebugServer listenerCount])
-        [[WebScriptDebugServer sharedScriptDebugServer] webView:getWebView(m_webFrame.get())
-            didLoadMainResourceForDataSource:dataSource(loader)];
+        [[WebScriptDebugServer sharedScriptDebugServer] webView:getWebView(m_webFrame.get()) didLoadMainResourceForDataSource:dataSource(loader)];
 }
 
 void WebFrameLoaderClient::revertToProvisionalState(DocumentLoader* loader)
diff --git a/WebKit/WebView/WebHTMLView.mm b/WebKit/WebView/WebHTMLView.mm
index cbc05f7..535d85e 100644
--- a/WebKit/WebView/WebHTMLView.mm
+++ b/WebKit/WebView/WebHTMLView.mm
@@ -2058,13 +2058,8 @@
     _private->selectorForDoCommandBySelector = 0;
     if (callerAlreadyCalledDelegate)
         return NO;
-
     WebView *webView = [self _webView];
-    id editingDelegate = [webView editingDelegate];
-    if (![editingDelegate respondsToSelector:@selector(webView:doCommandBySelector:)])
-        return NO;
-
-    return [editingDelegate webView:webView doCommandBySelector:selector];
+    return [[webView _editingDelegateForwarder] webView:webView doCommandBySelector:selector];
 }
 
 - (void)callWebCoreCommand:(SEL)selector
@@ -2450,12 +2445,7 @@
 - (BOOL)validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item
 {
     BOOL result = [self validateUserInterfaceItemWithoutDelegate:item];
-
-    id ud = [[self _webView] UIDelegate];
-    if (ud && [ud respondsToSelector:@selector(webView:validateUserInterfaceItem:defaultValidation:)])
-        return [ud webView:[self _webView] validateUserInterfaceItem:item defaultValidation:result];
-
-    return result;
+    return CallUIDelegateReturningBoolean(result, [self _webView], @selector(webView:validateUserInterfaceItem:defaultValidation:), item, result);
 }
 
 - (BOOL)acceptsFirstResponder
diff --git a/WebKit/WebView/WebPDFView.mm b/WebKit/WebView/WebPDFView.mm
index 9c7cb93..ccc1796 100644
--- a/WebKit/WebView/WebPDFView.mm
+++ b/WebKit/WebView/WebPDFView.mm
@@ -493,12 +493,7 @@
 - (BOOL)validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item
 {
     BOOL result = [self validateUserInterfaceItemWithoutDelegate:item];
-
-    id ud = [[self _webView] UIDelegate];
-    if (ud && [ud respondsToSelector:@selector(webView:validateUserInterfaceItem:defaultValidation:)])
-        return [ud webView:[self _webView] validateUserInterfaceItem:item defaultValidation:result];
-
-    return result;
+    return CallUIDelegateReturningBoolean(result, [self _webView], @selector(webView:validateUserInterfaceItem:defaultValidation:), item, result);
 }
 
 #pragma mark INTERFACE BUILDER ACTIONS FOR SAFARI
@@ -982,10 +977,7 @@
 
     // Delegate method sent when the user requests downloading the PDF file to disk. We pass NO for
     // showingPanel: so that the PDF file is saved to the standard location without user intervention.
-    id UIDelegate = [[self _webView] UIDelegate];
-
-    if (UIDelegate && [UIDelegate respondsToSelector:@selector(webView:saveFrameView:showingPanel:)])
-        [UIDelegate webView:[self _webView] saveFrameView:[[dataSource webFrame] frameView] showingPanel:NO];
+    CallUIDelegate([self _webView], @selector(webView:saveFrameView:showingPanel:), [[dataSource webFrame] frameView], NO);
 }
 
 @end
diff --git a/WebKit/WebView/WebView.mm b/WebKit/WebView/WebView.mm
index de027fb..7c159a3 100644
--- a/WebKit/WebView/WebView.mm
+++ b/WebKit/WebView/WebView.mm
@@ -259,6 +259,15 @@
 - (BOOL)validateUserInterfaceItemWithoutDelegate:(id <NSValidatedUserInterfaceItem>)item;
 @end
 
+@interface _WebSafeForwarder : NSObject
+{
+    id target; // Non-retained. Don't retain delegates.
+    id defaultTarget;
+    BOOL catchExceptions;
+}
+- (id)initWithTarget:(id)target defaultTarget:(id)defaultTarget catchExceptions:(BOOL)catchExceptions;
+@end
+
 @interface WebViewPrivate : NSObject
 {
 @public
@@ -289,7 +298,7 @@
     WebPreferences *preferences;
     BOOL useSiteSpecificSpoofing;
         
-    BOOL lastElementWasNonNil;
+    BOOL lastElementWasNil;
 
     NSWindow *hostWindow;
 
@@ -310,6 +319,7 @@
     BOOL becomingFirstResponderFromOutside;
     BOOL hoverFeedbackSuspended;
     BOOL usesPageCache;
+    BOOL catchesDelegateExceptions;
 
     NSColor *backgroundColor;
 
@@ -345,6 +355,9 @@
 - (void)_notifyTextSizeMultiplierChanged;
 @end
 
+@interface WebView (WebCallDelegateFunctions)
+@end
+
 NSString *WebElementDOMNodeKey =            @"WebElementDOMNode";
 NSString *WebElementFrameKey =              @"WebElementFrame";
 NSString *WebElementImageKey =              @"WebElementImage";
@@ -751,16 +764,11 @@
 
 - (WebView *)_openNewWindowWithRequest:(NSURLRequest *)request
 {
-    id wd = [self UIDelegate];
-    WebView *newWindowWebView = nil;
-    if ([wd respondsToSelector:@selector(webView:createWebViewWithRequest:)])
-        newWindowWebView = [wd webView:self createWebViewWithRequest:request];
-    else {
-        newWindowWebView = [[WebDefaultUIDelegate sharedUIDelegate] webView:self createWebViewWithRequest: request];
-    }
+    WebView *newWindowWebView = CallUIDelegate(self, @selector(webView:createWebViewWithRequest:), request);
+    if (!newWindowWebView)
+        return nil;
 
-    [[newWindowWebView _UIDelegateForwarder] webViewShow: newWindowWebView];
-
+    CallUIDelegate(newWindowWebView, @selector(webViewShow:));
     return newWindowWebView;
 }
 
@@ -771,24 +779,21 @@
 
 - (NSMenu *)_menuForElement:(NSDictionary *)element defaultItems:(NSArray *)items
 {
-    NSArray *defaultMenuItems = [[WebDefaultUIDelegate sharedUIDelegate]
-          webView:self contextMenuItemsForElement:element defaultMenuItems:items];
-    NSArray *menuItems = defaultMenuItems;
-    NSMenu *menu = nil;
-    unsigned i;
+    NSArray *defaultMenuItems = [[WebDefaultUIDelegate sharedUIDelegate] webView:self contextMenuItemsForElement:element defaultMenuItems:items];
 
-    if ([_private->UIDelegate respondsToSelector:@selector(webView:contextMenuItemsForElement:defaultMenuItems:)])
-        menuItems = [_private->UIDelegate webView:self contextMenuItemsForElement:element defaultMenuItems:defaultMenuItems];
+    NSArray *menuItems = CallUIDelegate(self, @selector(webView:contextMenuItemsForElement:defaultMenuItems:), element, defaultMenuItems);
+    if (!menuItems)
+        return nil;
 
-    if (menuItems && [menuItems count] > 0) {
-        menu = [[[NSMenu alloc] init] autorelease];
+    unsigned count = [menuItems count];
+    if (!count)
+        return nil;
 
-        for (i=0; i<[menuItems count]; i++) {
-            [menu addItem:[menuItems objectAtIndex:i]];
-        }
-    }
+    NSMenu *menu = [[NSMenu alloc] init];
+    for (unsigned i = 0; i < count; i++)
+        [menu addItem:[menuItems objectAtIndex:i]];
 
-    return menu;
+    return [menu autorelease];
 }
 
 - (void)_mouseDidMoveOverElement:(NSDictionary *)dictionary modifierFlags:(NSUInteger)modifierFlags
@@ -796,15 +801,14 @@
     // When the mouse isn't over this view at all, we'll get called with a dictionary of nil over
     // and over again. So it's a good idea to catch that here and not send multiple calls to the delegate
     // for that case.
-    
-    if (dictionary && _private->lastElementWasNonNil) {
-        [[self _UIDelegateForwarder] webView:self mouseDidMoveOverElement:dictionary modifierFlags:modifierFlags];
-    }
-    _private->lastElementWasNonNil = dictionary != nil;
+    if (!dictionary && _private->lastElementWasNil)
+        return;
+
+    _private->lastElementWasNil = !dictionary;
+
+    CallUIDelegate(self, @selector(webView:mouseDidMoveOverElement:modifierFlags:), dictionary, modifierFlags);
 }
 
-
-
 - (void)_loadBackForwardListFromOtherView:(WebView *)otherView
 {
     if (!_private->page)
@@ -933,52 +937,39 @@
 - (void)_cacheResourceLoadDelegateImplementations
 {
     WebResourceDelegateImplementationCache *cache = &_private->resourceLoadDelegateImplementations;
-    id delegate = [self resourceLoadDelegate];
+    id delegate = _private->resourceProgressDelegate;
     Class delegateClass = [delegate class];
 
-    cache->delegateImplementsDidCancelAuthenticationChallenge = [delegate respondsToSelector:@selector(webView:resource:didCancelAuthenticationChallenge:fromDataSource:)];
-    cache->delegateImplementsDidReceiveAuthenticationChallenge = [delegate respondsToSelector:@selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:)];
-    cache->delegateImplementsDidFinishLoadingFromDataSource = [delegate respondsToSelector:@selector(webView:resource:didFinishLoadingFromDataSource:)];
-    cache->delegateImplementsDidFailLoadingWithErrorFromDataSource = [delegate respondsToSelector:@selector(webView:resource:didFailLoadingWithError:fromDataSource:)];
-    cache->delegateImplementsDidReceiveContentLength = [delegate respondsToSelector:@selector(webView:resource:didReceiveContentLength:fromDataSource:)];
-    cache->delegateImplementsDidReceiveResponse = [delegate respondsToSelector:@selector(webView:resource:didReceiveResponse:fromDataSource:)];
-    cache->delegateImplementsWillSendRequest = [delegate respondsToSelector:@selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:)];
-    cache->delegateImplementsIdentifierForRequest = [delegate respondsToSelector:@selector(webView:identifierForInitialRequest:fromDataSource:)];
-    cache->delegateImplementsDidLoadResourceFromMemoryCache = [delegate respondsToSelector:@selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:)];
-    cache->delegateImplementsWillCacheResponse = [delegate respondsToSelector:@selector(webView:resource:willCacheResponse:fromDataSource:)];
-
 #if defined(OBJC_API_VERSION) && OBJC_API_VERSION > 0
 #define GET_OBJC_METHOD_IMP(class,selector) class_getMethodImplementation(class, selector)
 #else
 #define GET_OBJC_METHOD_IMP(class,selector) class_getInstanceMethod(class, selector)->method_imp
 #endif
 
-    if (cache->delegateImplementsDidCancelAuthenticationChallenge)
-        cache->didCancelAuthenticationChallengeFunc = (WebDidCancelAuthenticationChallengeFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:));
-    if (cache->delegateImplementsDidReceiveAuthenticationChallenge)
-        cache->didReceiveAuthenticationChallengeFunc = (WebDidReceiveAuthenticationChallengeFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:));
-    if (cache->delegateImplementsDidFinishLoadingFromDataSource)
-        cache->didFinishLoadingFromDataSourceFunc = (WebDidFinishLoadingFromDataSourceFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didFinishLoadingFromDataSource:));
-    if (cache->delegateImplementsDidFailLoadingWithErrorFromDataSource)
-        cache->didFailLoadingWithErrorFromDataSourceFunc = (WebDidFailLoadingWithErrorFromDataSourceFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didFailLoadingWithError:fromDataSource:));
-    if (cache->delegateImplementsDidReceiveContentLength)
-        cache->didReceiveContentLengthFunc = (WebDidReceiveContentLengthFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveContentLength:fromDataSource:));
-    if (cache->delegateImplementsDidReceiveResponse)
-        cache->didReceiveResponseFunc = (WebDidReceiveResponseFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveResponse:fromDataSource:));
-    if (cache->delegateImplementsWillSendRequest)
-        cache->willSendRequestFunc = (WebWillSendRequestFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:));
-    if (cache->delegateImplementsIdentifierForRequest)
-        cache->identifierForRequestFunc = (WebIdentifierForRequestFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:identifierForInitialRequest:fromDataSource:));
-    if (cache->delegateImplementsDidLoadResourceFromMemoryCache)
-        cache->didLoadResourceFromMemoryCacheFunc = (WebDidLoadResourceFromMemoryCacheFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:));
-    if (cache->delegateImplementsWillCacheResponse)
-        cache->willCacheResponseFunc = (WebWillCacheResponseFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:willCacheResponse:fromDataSource:));
-#undef GET_OBJC_METHOD_IMP
-}
+    if ([delegate respondsToSelector:@selector(webView:resource:didCancelAuthenticationChallenge:fromDataSource:)])
+        cache->didCancelAuthenticationChallengeFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:)])
+        cache->didReceiveAuthenticationChallengeFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:resource:didFinishLoadingFromDataSource:)])
+        cache->didFinishLoadingFromDataSourceFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didFinishLoadingFromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:resource:didFailLoadingWithError:fromDataSource:)])
+        cache->didFailLoadingWithErrorFromDataSourceFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didFailLoadingWithError:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:resource:didReceiveContentLength:fromDataSource:)])
+        cache->didReceiveContentLengthFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveContentLength:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:resource:didReceiveResponse:fromDataSource:)])
+        cache->didReceiveResponseFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:didReceiveResponse:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:)])
+        cache->willSendRequestFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:identifierForInitialRequest:fromDataSource:)])
+        cache->identifierForRequestFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:identifierForInitialRequest:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:)])
+        cache->didLoadResourceFromMemoryCacheFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:resource:willCacheResponse:fromDataSource:)])
+        cache->willCacheResponseFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:resource:willCacheResponse:fromDataSource:));
+    if ([delegate respondsToSelector:@selector(webView:plugInFailedWithError:dataSource:)])
+        cache->plugInFailedWithErrorFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:plugInFailedWithError:dataSource:));
 
-id WebViewGetResourceLoadDelegate(WebView *webView)
-{
-    return webView->_private->resourceProgressDelegate;
+#undef GET_OBJC_METHOD_IMP
 }
 
 WebResourceDelegateImplementationCache WebViewGetResourceLoadDelegateImplementations(WebView *webView)
@@ -989,73 +980,51 @@
 - (void)_cacheFrameLoadDelegateImplementations
 {
     WebFrameLoadDelegateImplementationCache *cache = &_private->frameLoadDelegateImplementations;
-    id delegate = [self frameLoadDelegate];
+    id delegate = _private->frameLoadDelegate;
     Class delegateClass = [delegate class];
 
-    cache->delegateImplementsDidClearWindowObjectForFrame = [delegate respondsToSelector:@selector(webView:didClearWindowObject:forFrame:)];
-    cache->delegateImplementsWindowScriptObjectAvailable = [delegate respondsToSelector:@selector(webView:windowScriptObjectAvailable:)];
-    cache->delegateImplementsDidHandleOnloadEventsForFrame = [delegate respondsToSelector:@selector(webView:didHandleOnloadEventsForFrame:)];
-    cache->delegateImplementsDidReceiveServerRedirectForProvisionalLoadForFrame = [delegate respondsToSelector:@selector(webView:didReceiveServerRedirectForProvisionalLoadForFrame:)];
-    cache->delegateImplementsDidCancelClientRedirectForFrame = [delegate respondsToSelector:@selector(webView:didCancelClientRedirectForFrame:)];
-    cache->delegateImplementsWillPerformClientRedirectToURLDelayFireDateForFrame = [delegate respondsToSelector:@selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:)];
-    cache->delegateImplementsDidChangeLocationWithinPageForFrame = [delegate respondsToSelector:@selector(webView:didChangeLocationWithinPageForFrame:)];
-    cache->delegateImplementsWillCloseFrame = [delegate respondsToSelector:@selector(webView:willCloseFrame:)];
-    cache->delegateImplementsDidStartProvisionalLoadForFrame = [delegate respondsToSelector:@selector(webView:didStartProvisionalLoadForFrame:)];
-    cache->delegateImplementsDidReceiveTitleForFrame = [delegate respondsToSelector:@selector(webView:didReceiveTitle:forFrame:)];
-    cache->delegateImplementsDidCommitLoadForFrame = [delegate respondsToSelector:@selector(webView:didCommitLoadForFrame:)];
-    cache->delegateImplementsDidFailProvisionalLoadWithErrorForFrame = [delegate respondsToSelector:@selector(webView:didFailProvisionalLoadWithError:forFrame:)];
-    cache->delegateImplementsDidFailLoadWithErrorForFrame = [delegate respondsToSelector:@selector(webView:didFailLoadWithError:forFrame:)];
-    cache->delegateImplementsDidFinishLoadForFrame = [delegate respondsToSelector:@selector(webView:didFinishLoadForFrame:)];
-    cache->delegateImplementsDidFirstLayoutInFrame = [delegate respondsToSelector:@selector(webView:didFirstLayoutInFrame:)];
-    cache->delegateImplementsDidReceiveIconForFrame = [delegate respondsToSelector:@selector(webView:didReceiveIcon:forFrame:)];
-    cache->delegateImplementsDidFinishDocumentLoadForFrame = [delegate respondsToSelector:@selector(webView:didFinishDocumentLoadForFrame:)];
-
 #if defined(OBJC_API_VERSION) && OBJC_API_VERSION > 0
 #define GET_OBJC_METHOD_IMP(class,selector) class_getMethodImplementation(class, selector)
 #else
 #define GET_OBJC_METHOD_IMP(class,selector) class_getInstanceMethod(class, selector)->method_imp
 #endif
 
-    if (cache->delegateImplementsDidClearWindowObjectForFrame)
-        cache->didClearWindowObjectForFrameFunc = (WebDidClearWindowObjectForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didClearWindowObject:forFrame:));
-    if (cache->delegateImplementsWindowScriptObjectAvailable)
-        cache->windowScriptObjectAvailableFunc = (WebWindowScriptObjectAvailableFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:windowScriptObjectAvailable:));
-    if (cache->delegateImplementsDidHandleOnloadEventsForFrame)
-        cache->didHandleOnloadEventsForFrameFunc = (WebDidHandleOnloadEventsForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didHandleOnloadEventsForFrame:));
-    if (cache->delegateImplementsDidReceiveServerRedirectForProvisionalLoadForFrame)
-        cache->didReceiveServerRedirectForProvisionalLoadForFrameFunc = (WebDidReceiveServerRedirectForProvisionalLoadForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didReceiveServerRedirectForProvisionalLoadForFrame:));
-    if (cache->delegateImplementsDidCancelClientRedirectForFrame)
-        cache->didCancelClientRedirectForFrameFunc = (WebDidCancelClientRedirectForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didCancelClientRedirectForFrame:));
-    if (cache->delegateImplementsWillPerformClientRedirectToURLDelayFireDateForFrame)
-        cache->willPerformClientRedirectToURLDelayFireDateForFrameFunc = (WebWillPerformClientRedirectToURLDelayFireDateForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:));
-    if (cache->delegateImplementsDidChangeLocationWithinPageForFrame)
-        cache->didChangeLocationWithinPageForFrameFunc = (WebDidChangeLocationWithinPageForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didChangeLocationWithinPageForFrame:));
-    if (cache->delegateImplementsWillCloseFrame)
-        cache->willCloseFrameFunc = (WebWillCloseFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:willCloseFrame:));
-    if (cache->delegateImplementsDidStartProvisionalLoadForFrame)
-        cache->didStartProvisionalLoadForFrameFunc = (WebDidStartProvisionalLoadForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didStartProvisionalLoadForFrame:));
-    if (cache->delegateImplementsDidReceiveTitleForFrame)
-        cache->didReceiveTitleForFrameFunc = (WebDidReceiveTitleForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didReceiveTitle:forFrame:));
-    if (cache->delegateImplementsDidCommitLoadForFrame)
-        cache->didCommitLoadForFrameFunc = (WebDidCommitLoadForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didCommitLoadForFrame:));
-    if (cache->delegateImplementsDidFailProvisionalLoadWithErrorForFrame)
-        cache->didFailProvisionalLoadWithErrorForFrameFunc = (WebDidFailProvisionalLoadWithErrorForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFailProvisionalLoadWithError:forFrame:));
-    if (cache->delegateImplementsDidFailLoadWithErrorForFrame)
-        cache->didFailLoadWithErrorForFrameFunc = (WebDidFailLoadWithErrorForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFailLoadWithError:forFrame:));
-    if (cache->delegateImplementsDidFinishLoadForFrame)
-        cache->didFinishLoadForFrameFunc = (WebDidFinishLoadForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFinishLoadForFrame:));
-    if (cache->delegateImplementsDidFirstLayoutInFrame)
-        cache->didFirstLayoutInFrameFunc = (WebDidFirstLayoutInFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFirstLayoutInFrame:));
-    if (cache->delegateImplementsDidReceiveIconForFrame)
-        cache->didReceiveIconForFrameFunc = (WebDidReceiveIconForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didReceiveIcon:forFrame:));
-    if (cache->delegateImplementsDidFinishDocumentLoadForFrame)
-        cache->didFinishDocumentLoadForFrameFunc = (WebDidFinishDocumentLoadForFrameFunc)GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFinishDocumentLoadForFrame:));
-#undef GET_OBJC_METHOD_IMP
-}
+    if ([delegate respondsToSelector:@selector(webView:didClearWindowObject:forFrame:)])
+        cache->didClearWindowObjectForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didClearWindowObject:forFrame:));
+    if ([delegate respondsToSelector:@selector(webView:windowScriptObjectAvailable:)])
+        cache->windowScriptObjectAvailableFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:windowScriptObjectAvailable:));
+    if ([delegate respondsToSelector:@selector(webView:didHandleOnloadEventsForFrame:)])
+        cache->didHandleOnloadEventsForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didHandleOnloadEventsForFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didReceiveServerRedirectForProvisionalLoadForFrame:)])
+        cache->didReceiveServerRedirectForProvisionalLoadForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didReceiveServerRedirectForProvisionalLoadForFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didCancelClientRedirectForFrame:)])
+        cache->didCancelClientRedirectForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didCancelClientRedirectForFrame:));
+    if ([delegate respondsToSelector:@selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:)])
+        cache->willPerformClientRedirectToURLDelayFireDateForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didChangeLocationWithinPageForFrame:)])
+        cache->didChangeLocationWithinPageForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didChangeLocationWithinPageForFrame:));
+    if ([delegate respondsToSelector:@selector(webView:willCloseFrame:)])
+        cache->willCloseFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:willCloseFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didStartProvisionalLoadForFrame:)])
+        cache->didStartProvisionalLoadForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didStartProvisionalLoadForFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didReceiveTitle:forFrame:)])
+        cache->didReceiveTitleForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didReceiveTitle:forFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didCommitLoadForFrame:)])
+        cache->didCommitLoadForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didCommitLoadForFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didFailProvisionalLoadWithError:forFrame:)])
+        cache->didFailProvisionalLoadWithErrorForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFailProvisionalLoadWithError:forFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didFailLoadWithError:forFrame:)])
+        cache->didFailLoadWithErrorForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFailLoadWithError:forFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didFinishLoadForFrame:)])
+        cache->didFinishLoadForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFinishLoadForFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didFirstLayoutInFrame:)])
+        cache->didFirstLayoutInFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFirstLayoutInFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didReceiveIcon:forFrame:)])
+        cache->didReceiveIconForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didReceiveIcon:forFrame:));
+    if ([delegate respondsToSelector:@selector(webView:didFinishDocumentLoadForFrame:)])
+        cache->didFinishDocumentLoadForFrameFunc = GET_OBJC_METHOD_IMP(delegateClass, @selector(webView:didFinishDocumentLoadForFrame:));
 
-id WebViewGetFrameLoadDelegate(WebView *webView)
-{
-    return webView->_private->frameLoadDelegate;
+#undef GET_OBJC_METHOD_IMP
 }
 
 WebFrameLoadDelegateImplementationCache WebViewGetFrameLoadDelegateImplementations(WebView *webView)
@@ -1063,35 +1032,36 @@
     return webView->_private->frameLoadDelegateImplementations;
 }
 
-- _policyDelegateForwarder
+- (id)_policyDelegateForwarder
 {
     if (!_private->policyDelegateForwarder)
-        _private->policyDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget: [self policyDelegate] defaultTarget: [WebDefaultPolicyDelegate sharedPolicyDelegate] templateClass: [WebDefaultPolicyDelegate class]];
+        _private->policyDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->policyDelegate defaultTarget:[WebDefaultPolicyDelegate sharedPolicyDelegate] catchExceptions:_private->catchesDelegateExceptions];
     return _private->policyDelegateForwarder;
 }
 
-- _UIDelegateForwarder
+- (id)_UIDelegateForwarder
 {
     if (!_private->UIDelegateForwarder)
-        _private->UIDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget: [self UIDelegate] defaultTarget: [WebDefaultUIDelegate sharedUIDelegate] templateClass: [WebDefaultUIDelegate class]];
+        _private->UIDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->UIDelegate defaultTarget:[WebDefaultUIDelegate sharedUIDelegate] catchExceptions:_private->catchesDelegateExceptions];
     return _private->UIDelegateForwarder;
 }
 
-- _editingDelegateForwarder
+- (id)_editingDelegateForwarder
 {
     // This can be called during window deallocation by QTMovieView in the QuickTime Cocoa Plug-in.
     // Not sure if that is a bug or not.
     if (!_private)
         return nil;
+
     if (!_private->editingDelegateForwarder)
-        _private->editingDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget: [self editingDelegate] defaultTarget: [WebDefaultEditingDelegate sharedEditingDelegate] templateClass: [WebDefaultEditingDelegate class]];
+        _private->editingDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->editingDelegate defaultTarget:[WebDefaultEditingDelegate sharedEditingDelegate] catchExceptions:_private->catchesDelegateExceptions];
     return _private->editingDelegateForwarder;
 }
 
-- _scriptDebugDelegateForwarder
+- (id)_scriptDebugDelegateForwarder
 {
     if (!_private->scriptDebugDelegateForwarder)
-        _private->scriptDebugDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget: [self scriptDebugDelegate] defaultTarget: [WebDefaultScriptDebugDelegate sharedScriptDebugDelegate] templateClass: [WebDefaultScriptDebugDelegate class]];
+        _private->scriptDebugDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->scriptDebugDelegate defaultTarget:[WebDefaultScriptDebugDelegate sharedScriptDebugDelegate] catchExceptions:_private->catchesDelegateExceptions];
     return _private->scriptDebugDelegateForwarder;
 }
 
@@ -1615,55 +1585,56 @@
     _private->page->clearUndoRedoOperations();
 }
 
+- (void)_setCatchesDelegateExceptions:(BOOL)f
+{
+    _private->catchesDelegateExceptions = f;
+}
+
+- (BOOL)_catchesDelegateExceptions
+{
+    return _private->catchesDelegateExceptions;
+}
+
 @end
 
 @implementation _WebSafeForwarder
 
-- initWithTarget: t defaultTarget: dt templateClass: (Class)aClass
+// Used to send messages to delegates that implement informal protocols.
+
+- (id)initWithTarget:(id)t defaultTarget:(id)dt catchExceptions:(BOOL)c
 {
     self = [super init];
     if (!self)
         return nil;
-    
     target = t; // Non retained.
     defaultTarget = dt;
-    templateClass = aClass;
+    catchExceptions = c;
     return self;
 }
 
-// Used to send messages to delegates that implement informal protocols.
-+ safeForwarderWithTarget: t defaultTarget: dt templateClass: (Class)aClass;
+- (void)forwardInvocation:(NSInvocation *)invocation
 {
-    return [[[_WebSafeForwarder alloc] initWithTarget: t defaultTarget: dt templateClass: aClass] autorelease];
-}
-
-#ifndef NDEBUG
-NSMutableDictionary *countInvocations;
-#endif
-
-- (void)forwardInvocation:(NSInvocation *)anInvocation
-{
-#ifndef NDEBUG
-    if (!countInvocations){
-        countInvocations = [[NSMutableDictionary alloc] init];
+    if ([target respondsToSelector:[invocation selector]]) {
+        if (catchExceptions) {
+            @try {
+                [invocation invokeWithTarget:target];
+            } @catch(id exception) {
+                ReportDiscardedDelegateException([invocation selector], exception);
+            }
+        } else
+            [invocation invokeWithTarget:target];
+        return;
     }
-    NSNumber *count = [countInvocations objectForKey: NSStringFromSelector([anInvocation selector])];
-    if (!count)
-        count = [NSNumber numberWithInt: 1];
-    else
-        count = [NSNumber numberWithInt: [count intValue] + 1];
-    [countInvocations setObject: count forKey: NSStringFromSelector([anInvocation selector])];
-#endif
-    if ([target respondsToSelector: [anInvocation selector]])
-        [anInvocation invokeWithTarget: target];
-    else if ([defaultTarget respondsToSelector: [anInvocation selector]])
-        [anInvocation invokeWithTarget: defaultTarget];
+
+    if ([defaultTarget respondsToSelector:[invocation selector]])
+        [invocation invokeWithTarget:defaultTarget];
+
     // Do nothing quietly if method not implemented.
 }
 
 - (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector
 {
-    return [templateClass instanceMethodSignatureForSelector: aSelector];
+    return [defaultTarget methodSignatureForSelector:aSelector];
 }
 
 @end
@@ -1822,6 +1793,7 @@
 
 - (void)_commonInitializationWithFrameName:(NSString *)frameName groupName:(NSString *)groupName
 {
+    _private->catchesDelegateExceptions = YES;
     _private->mainFrameDocumentReady = NO;
     _private->drawsBackground = YES;
     _private->smartInsertDeleteEnabled = YES;
@@ -2846,12 +2818,7 @@
 - (BOOL)validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item
 {
     BOOL result = [self validateUserInterfaceItemWithoutDelegate:item];
-
-    id ud = [self UIDelegate];
-    if (ud && [ud respondsToSelector:@selector(webView:validateUserInterfaceItem:defaultValidation:)])
-        return [ud webView:self validateUserInterfaceItem:item defaultValidation:result];
-
-    return result;
+    return CallUIDelegateReturningBoolean(result, self, @selector(webView:validateUserInterfaceItem:defaultValidation:), item, result);
 }
 
 @end
@@ -3115,28 +3082,12 @@
 
 - (float)_headerHeight
 {
-    if ([[self UIDelegate] respondsToSelector:@selector(webViewHeaderHeight:)]) {
-        return [[self UIDelegate] webViewHeaderHeight:self];
-    }
-    
-#ifdef DEBUG_HEADER_AND_FOOTER
-    return 25;
-#else
-    return 0;
-#endif
+    return CallUIDelegateReturningFloat(self, @selector(webViewHeaderHeight:));
 }
 
 - (float)_footerHeight
 {
-    if ([[self UIDelegate] respondsToSelector:@selector(webViewFooterHeight:)]) {
-        return [[self UIDelegate] webViewFooterHeight:self];
-    }
-    
-#ifdef DEBUG_HEADER_AND_FOOTER
-    return 50;
-#else
-    return 0;
-#endif
+    return CallUIDelegateReturningFloat(self, @selector(webViewFooterHeight:));
 }
 
 - (void)_drawHeaderInRect:(NSRect)rect
@@ -3148,14 +3099,18 @@
     NSRectFill(rect);
     [currentContext restoreGraphicsState];
 #endif
-    
-    if ([[self UIDelegate] respondsToSelector:@selector(webView:drawHeaderInRect:)]) {
-        NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
-        [currentContext saveGraphicsState];
-        NSRectClip(rect);
-        [[self UIDelegate] webView:self drawHeaderInRect:rect]; 
-        [currentContext restoreGraphicsState];
-    }
+
+    SEL selector = @selector(webView:drawHeaderInRect:);
+    if (![_private->UIDelegate respondsToSelector:selector])
+        return;
+
+    NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
+    [currentContext saveGraphicsState];
+
+    NSRectClip(rect);
+    CallUIDelegate(self, selector, rect);
+
+    [currentContext restoreGraphicsState];
 }
 
 - (void)_drawFooterInRect:(NSRect)rect
@@ -3168,13 +3123,17 @@
     [currentContext restoreGraphicsState];
 #endif
     
-    if ([[self UIDelegate] respondsToSelector:@selector(webView:drawFooterInRect:)]) {
-        NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
-        [currentContext saveGraphicsState];
-        NSRectClip(rect);
-        [[self UIDelegate] webView:self drawFooterInRect:rect];
-        [currentContext restoreGraphicsState];
-    }
+    SEL selector = @selector(webView:drawFooterInRect:);
+    if (![_private->UIDelegate respondsToSelector:selector])
+        return;
+
+    NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
+    [currentContext saveGraphicsState];
+
+    NSRectClip(rect);
+    CallUIDelegate(self, selector, rect);
+
+    [currentContext restoreGraphicsState];
 }
 
 - (void)_adjustPrintingMarginsForHeaderAndFooter
@@ -3275,7 +3234,6 @@
     // FIXME: This quirk is needed due to <rdar://problem/4985321> - We can phase it out once Aperture can adopt the new behavior on their end
     if (!WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITHOUT_APERTURE_QUIRK) && [[[NSBundle mainBundle] bundleIdentifier] isEqualToString:@"com.apple.Aperture"])
         return YES;
-        
     return [[self _editingDelegateForwarder] webView:self shouldChangeSelectedDOMRange:currentRange toDOMRange:proposedRange affinity:selectionAffinity stillSelecting:flag];
 }
 
@@ -3917,3 +3875,458 @@
 }
 
 @end
+
+// We use these functions to call the delegates and block exceptions. These functions are
+// declared inside a WebView category to get direct access to the delegate data memebers,
+// preventing more ObjC message dispatch and compensating for the expense of the @try/@catch.
+
+@implementation WebView (WebCallDelegateFunctions)
+
+#if !(defined(__i386__) || defined(__x86_64__))
+typedef double (*ObjCMsgSendFPRet)(id, SEL, ...);
+static const ObjCMsgSendFPRet objc_msgSend_fpret = reinterpret_cast<ObjCMsgSendFPRet>(objc_msgSend);
+#endif
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, self);
+    @try {
+        return objc_msgSend(delegate, selector, self);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, self, object);
+    @try {
+        return objc_msgSend(delegate, selector, self, object);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, NSRect rect)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return reinterpret_cast<id (*)(id, SEL, WebView *, NSRect)>(objc_msgSend)(delegate, selector, self, rect);
+    @try {
+        return reinterpret_cast<id (*)(id, SEL, WebView *, NSRect)>(objc_msgSend)(delegate, selector, self, rect);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object1, id object2)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, self, object1, object2);
+    @try {
+        return objc_msgSend(delegate, selector, self, object1, object2);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object, BOOL boolean)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, self, object, boolean);
+    @try {
+        return objc_msgSend(delegate, selector, self, object, boolean);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object1, id object2, id object3)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, self, object1, object2, object3);
+    @try {
+        return objc_msgSend(delegate, selector, self, object1, object2, object3);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object, NSUInteger integer)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, self, object, integer);
+    @try {
+        return objc_msgSend(delegate, selector, self, object, integer);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline float CallDelegateReturningFloat(WebView *self, id delegate, SEL selector)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return 0.0f;
+    if (!self->_private->catchesDelegateExceptions)
+        return static_cast<float>(objc_msgSend_fpret(delegate, selector, self));
+    @try {
+        return static_cast<float>(objc_msgSend_fpret(delegate, selector, self));
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return 0.0f;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return result;
+    if (!self->_private->catchesDelegateExceptions)
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *)>(objc_msgSend)(delegate, selector, self);
+    @try {
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *)>(objc_msgSend)(delegate, selector, self);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return result;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector, id object)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return result;
+    if (!self->_private->catchesDelegateExceptions)
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id)>(objc_msgSend)(delegate, selector, self, object);
+    @try {
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id)>(objc_msgSend)(delegate, selector, self, object);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return result;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector, id object, BOOL boolean)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return result;
+    if (!self->_private->catchesDelegateExceptions)
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, BOOL)>(objc_msgSend)(delegate, selector, self, object, boolean);
+    @try {
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, BOOL)>(objc_msgSend)(delegate, selector, self, object, boolean);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return result;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector, id object1, id object2)
+{
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return result;
+    if (!self->_private->catchesDelegateExceptions)
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, id)>(objc_msgSend)(delegate, selector, self, object1, object2);
+    @try {
+        return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, id)>(objc_msgSend)(delegate, selector, self, object1, object2);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return result;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self);
+    @try {
+        return implementation(delegate, selector, self);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self, object);
+    @try {
+        return implementation(delegate, selector, self, object);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self, object1, object2);
+    @try {
+        return implementation(delegate, selector, self, object1, object2);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2, id object3)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self, object1, object2, object3);
+    @try {
+        return implementation(delegate, selector, self, object1, object2, object3);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2, id object3, id object4)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self, object1, object2, object3, object4);
+    @try {
+        return implementation(delegate, selector, self, object1, object2, object3, object4);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, NSInteger integer, id object2)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self, object1, integer, object2);
+    @try {
+        return implementation(delegate, selector, self, object1, integer, object2);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2, NSInteger integer, id object3)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self, object1, object2, integer, object3);
+    @try {
+        return implementation(delegate, selector, self, object1, object2, integer, object3);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, NSTimeInterval interval, id object2, id object3)
+{
+    if (!delegate)
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return implementation(delegate, selector, self, object1, interval, object2, object3);
+    @try {
+        return implementation(delegate, selector, self, object1, interval, object2, object3);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+id CallUIDelegate(WebView *self, SEL selector)
+{
+    return CallDelegate(self, self->_private->UIDelegate, selector);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object)
+{
+    return CallDelegate(self, self->_private->UIDelegate, selector, object);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object, BOOL boolean)
+{
+    return CallDelegate(self, self->_private->UIDelegate, selector, object, boolean);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, NSRect rect)
+{
+    return CallDelegate(self, self->_private->UIDelegate, selector, rect);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object1, id object2)
+{
+    return CallDelegate(self, self->_private->UIDelegate, selector, object1, object2);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object1, id object2, id object3)
+{
+    return CallDelegate(self, self->_private->UIDelegate, selector, object1, object2, object3);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object, NSUInteger integer)
+{
+    return CallDelegate(self, self->_private->UIDelegate, selector, object, integer);
+}
+
+float CallUIDelegateReturningFloat(WebView *self, SEL selector)
+{
+    return CallDelegateReturningFloat(self, self->_private->UIDelegate, selector);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector)
+{
+    return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object)
+{
+    return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector, object);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object, BOOL boolean)
+{
+    return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector, object, boolean);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object1, id object2)
+{
+    return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector, object1, object2);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector)
+{
+    return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object)
+{
+    return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2)
+{
+    return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, object2);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3)
+{
+    return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, object2, object3);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3, id object4)
+{
+    return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, object2, object3, object4);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, NSTimeInterval interval, id object2, id object3)
+{
+    return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, interval, object2, object3);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2)
+{
+    return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3)
+{
+    return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2, object3);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3, id object4)
+{
+    return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2, object3, object4);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, NSInteger integer, id object2)
+{
+    return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, integer, object2);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, NSInteger integer, id object3)
+{
+    return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2, integer, object3);
+}
+
+// The form delegate needs to have it's own implementation, because the first argument is never the WebView
+
+id CallFormDelegate(WebView *self, SEL selector, id object1, id object2)
+{
+    id delegate = self->_private->formDelegate;
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, object1, object2);
+    @try {
+        return objc_msgSend(delegate, selector, object1, object2);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+id CallFormDelegate(WebView *self, SEL selector, id object1, id object2, id object3, id object4, id object5)
+{
+    id delegate = self->_private->formDelegate;
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return nil;
+    if (!self->_private->catchesDelegateExceptions)
+        return objc_msgSend(delegate, selector, object1, object2, object3, object4, object5);
+    @try {
+        return objc_msgSend(delegate, selector, object1, object2, object3, object4, object5);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return nil;
+}
+
+BOOL CallFormDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object1, SEL selectorArg, id object2)
+{
+    id delegate = self->_private->formDelegate;
+    if (!delegate || ![delegate respondsToSelector:selector])
+        return result;
+    if (!self->_private->catchesDelegateExceptions)
+        return reinterpret_cast<BOOL (*)(id, SEL, id, SEL, id)>(objc_msgSend)(delegate, selector, object1, selectorArg, object2);
+    @try {
+        return reinterpret_cast<BOOL (*)(id, SEL, id, SEL, id)>(objc_msgSend)(delegate, selector, object1, selectorArg, object2);
+    } @catch(id exception) {
+        ReportDiscardedDelegateException(selector, exception);
+    }
+    return result;
+}
+
+@end
diff --git a/WebKit/WebView/WebViewInternal.h b/WebKit/WebView/WebViewInternal.h
index 50b2d21..171ae72 100644
--- a/WebKit/WebView/WebViewInternal.h
+++ b/WebKit/WebView/WebViewInternal.h
@@ -65,13 +65,8 @@
 #endif
 @end
 
-id WebViewGetResourceLoadDelegate(WebView *webView);
-WebResourceDelegateImplementationCache WebViewGetResourceLoadDelegateImplementations(WebView *webView);
-
-id WebViewGetFrameLoadDelegate(WebView *webView);
-WebFrameLoadDelegateImplementationCache WebViewGetFrameLoadDelegateImplementations(WebView *webView);
-
 @interface WebView (WebViewMiscInternal)
+
 + (void)_initializeCacheSizesIfNecessary;
 - (WebCorePage*)page;
 - (NSMenu *)_menuForElement:(NSDictionary *)element defaultItems:(NSArray *)items;
@@ -115,4 +110,76 @@
 - (id)_objectForIdentifier:(unsigned long)identifier;
 - (void)_removeObjectForIdentifier:(unsigned long)identifier;
 - (BOOL)_becomingFirstResponderFromOutside;
+
 @end
+
+typedef struct _WebResourceDelegateImplementationCache {
+    IMP didCancelAuthenticationChallengeFunc;
+    IMP didReceiveAuthenticationChallengeFunc;
+    IMP identifierForRequestFunc;
+    IMP willSendRequestFunc;
+    IMP didReceiveResponseFunc;
+    IMP didReceiveContentLengthFunc;
+    IMP didFinishLoadingFromDataSourceFunc;
+    IMP didFailLoadingWithErrorFromDataSourceFunc;
+    IMP didLoadResourceFromMemoryCacheFunc;
+    IMP willCacheResponseFunc;
+    IMP plugInFailedWithErrorFunc;
+} WebResourceDelegateImplementationCache;
+
+typedef struct _WebFrameLoadDelegateImplementationCache {
+    IMP didClearWindowObjectForFrameFunc;
+    IMP windowScriptObjectAvailableFunc;
+    IMP didHandleOnloadEventsForFrameFunc;
+    IMP didReceiveServerRedirectForProvisionalLoadForFrameFunc;
+    IMP didCancelClientRedirectForFrameFunc;
+    IMP willPerformClientRedirectToURLDelayFireDateForFrameFunc;
+    IMP didChangeLocationWithinPageForFrameFunc;
+    IMP willCloseFrameFunc;
+    IMP didStartProvisionalLoadForFrameFunc;
+    IMP didReceiveTitleForFrameFunc;
+    IMP didCommitLoadForFrameFunc;
+    IMP didFailProvisionalLoadWithErrorForFrameFunc;
+    IMP didFailLoadWithErrorForFrameFunc;
+    IMP didFinishLoadForFrameFunc;
+    IMP didFirstLayoutInFrameFunc;
+    IMP didReceiveIconForFrameFunc;
+    IMP didFinishDocumentLoadForFrameFunc;
+} WebFrameLoadDelegateImplementationCache;
+
+WebResourceDelegateImplementationCache WebViewGetResourceLoadDelegateImplementations(WebView *webView);
+WebFrameLoadDelegateImplementationCache WebViewGetFrameLoadDelegateImplementations(WebView *webView);
+
+#ifdef __cplusplus
+
+id CallFormDelegate(WebView *, SEL, id, id);
+id CallFormDelegate(WebView *self, SEL selector, id object1, id object2, id object3, id object4, id object5);
+BOOL CallFormDelegateReturningBoolean(BOOL, WebView *, SEL, id, SEL, id);
+
+id CallUIDelegate(WebView *, SEL);
+id CallUIDelegate(WebView *, SEL, id);
+id CallUIDelegate(WebView *, SEL, NSRect);
+id CallUIDelegate(WebView *, SEL, id, id);
+id CallUIDelegate(WebView *, SEL, id, BOOL);
+id CallUIDelegate(WebView *, SEL, id, id, id);
+id CallUIDelegate(WebView *, SEL, id, NSUInteger);
+float CallUIDelegateReturningFloat(WebView *, SEL);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL, id);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL, id, id);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL, id, BOOL);
+
+id CallFrameLoadDelegate(IMP, WebView *, SEL);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, id, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, id, id, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, NSTimeInterval, id, id);
+
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id, id, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, NSInteger, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id, NSInteger, id);
+
+#endif
diff --git a/WebKit/WebView/WebViewPrivate.h b/WebKit/WebView/WebViewPrivate.h
index d11e728..e312494 100644
--- a/WebKit/WebView/WebViewPrivate.h
+++ b/WebKit/WebView/WebViewPrivate.h
@@ -43,97 +43,6 @@
 
 @protocol WebFormDelegate;
 
-typedef void (*WebDidCancelAuthenticationChallengeFunc)(id, SEL, WebView *, id, NSURLAuthenticationChallenge *, WebDataSource *);
-typedef void (*WebDidReceiveAuthenticationChallengeFunc)(id, SEL, WebView *, id, NSURLAuthenticationChallenge *, WebDataSource *);
-typedef id (*WebIdentifierForRequestFunc)(id, SEL, WebView *, NSURLRequest *, WebDataSource *);
-typedef NSURLRequest *(*WebWillSendRequestFunc)(id, SEL, WebView *, id, NSURLRequest *, NSURLResponse *, WebDataSource *);
-typedef void (*WebDidReceiveResponseFunc)(id, SEL, WebView *, id, NSURLResponse *, WebDataSource *);
-typedef void (*WebDidReceiveContentLengthFunc)(id, SEL, WebView *, id, WebNSInteger, WebDataSource *);
-typedef void (*WebDidFinishLoadingFromDataSourceFunc)(id, SEL, WebView *, id, WebDataSource *);
-typedef void (*WebDidFailLoadingWithErrorFromDataSourceFunc)(id, SEL, WebView *, id, NSError *, WebDataSource *);
-typedef void (*WebDidLoadResourceFromMemoryCacheFunc)(id, SEL, WebView *, NSURLRequest *, NSURLResponse *, WebNSInteger, WebDataSource *);
-typedef NSCachedURLResponse *(*WebWillCacheResponseFunc)(id, SEL, WebView *, id, NSCachedURLResponse *, WebDataSource *);
-
-typedef struct _WebResourceDelegateImplementationCache {
-    uint delegateImplementsDidCancelAuthenticationChallenge:1;
-    uint delegateImplementsDidReceiveAuthenticationChallenge:1;
-    uint delegateImplementsDidReceiveResponse:1;
-    uint delegateImplementsDidReceiveContentLength:1;
-    uint delegateImplementsDidFinishLoadingFromDataSource:1;
-    uint delegateImplementsDidFailLoadingWithErrorFromDataSource:1;
-    uint delegateImplementsWillSendRequest:1;
-    uint delegateImplementsIdentifierForRequest:1;
-    uint delegateImplementsDidLoadResourceFromMemoryCache:1;
-    uint delegateImplementsWillCacheResponse:1;
-
-    WebDidCancelAuthenticationChallengeFunc didCancelAuthenticationChallengeFunc;
-    WebDidReceiveAuthenticationChallengeFunc didReceiveAuthenticationChallengeFunc;
-    WebIdentifierForRequestFunc identifierForRequestFunc;
-    WebWillSendRequestFunc willSendRequestFunc;
-    WebDidReceiveResponseFunc didReceiveResponseFunc;
-    WebDidReceiveContentLengthFunc didReceiveContentLengthFunc;
-    WebDidFinishLoadingFromDataSourceFunc didFinishLoadingFromDataSourceFunc;
-    WebDidFailLoadingWithErrorFromDataSourceFunc didFailLoadingWithErrorFromDataSourceFunc;
-    WebDidLoadResourceFromMemoryCacheFunc didLoadResourceFromMemoryCacheFunc;
-    WebWillCacheResponseFunc willCacheResponseFunc;
-} WebResourceDelegateImplementationCache;
-
-typedef void (*WebDidClearWindowObjectForFrameFunc)(id, SEL, WebView *, WebScriptObject *, WebFrame *);
-typedef void (*WebWindowScriptObjectAvailableFunc)(id, SEL, WebView *, WebScriptObject *);
-typedef void (*WebDidHandleOnloadEventsForFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebDidReceiveServerRedirectForProvisionalLoadForFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebDidCancelClientRedirectForFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebWillPerformClientRedirectToURLDelayFireDateForFrameFunc)(id, SEL, WebView *, NSURL *, double, NSDate *, WebFrame *);
-typedef void (*WebDidChangeLocationWithinPageForFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebWillCloseFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebDidStartProvisionalLoadForFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebDidReceiveTitleForFrameFunc)(id, SEL, WebView *, NSString *, WebFrame *);
-typedef void (*WebDidCommitLoadForFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebDidFailProvisionalLoadWithErrorForFrameFunc)(id, SEL, WebView *, NSError *, WebFrame *);
-typedef void (*WebDidFailLoadWithErrorForFrameFunc)(id, SEL, WebView *, NSError *, WebFrame *);
-typedef void (*WebDidFinishLoadForFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebDidFirstLayoutInFrameFunc)(id, SEL, WebView *, WebFrame *);
-typedef void (*WebDidReceiveIconForFrameFunc)(id, SEL, WebView *, NSImage *, WebFrame *);
-typedef void (*WebDidFinishDocumentLoadForFrameFunc)(id, SEL, WebView *, WebFrame *);
-
-typedef struct _WebFrameLoadDelegateImplementationCache {
-    uint delegateImplementsDidClearWindowObjectForFrame: 1;
-    uint delegateImplementsWindowScriptObjectAvailable: 1;
-    uint delegateImplementsDidHandleOnloadEventsForFrame: 1;
-    uint delegateImplementsDidReceiveServerRedirectForProvisionalLoadForFrame: 1;
-    uint delegateImplementsDidCancelClientRedirectForFrame: 1;
-    uint delegateImplementsWillPerformClientRedirectToURLDelayFireDateForFrame: 1;
-    uint delegateImplementsDidChangeLocationWithinPageForFrame: 1;
-    uint delegateImplementsWillCloseFrame: 1;
-    uint delegateImplementsDidStartProvisionalLoadForFrame: 1;
-    uint delegateImplementsDidReceiveTitleForFrame: 1;
-    uint delegateImplementsDidCommitLoadForFrame: 1;
-    uint delegateImplementsDidFailProvisionalLoadWithErrorForFrame: 1;
-    uint delegateImplementsDidFailLoadWithErrorForFrame: 1;
-    uint delegateImplementsDidFinishLoadForFrame: 1;
-    uint delegateImplementsDidFirstLayoutInFrame: 1;
-    uint delegateImplementsDidReceiveIconForFrame: 1;
-    uint delegateImplementsDidFinishDocumentLoadForFrame: 1;
-
-    WebDidClearWindowObjectForFrameFunc didClearWindowObjectForFrameFunc;
-    WebWindowScriptObjectAvailableFunc windowScriptObjectAvailableFunc;
-    WebDidHandleOnloadEventsForFrameFunc didHandleOnloadEventsForFrameFunc;
-    WebDidReceiveServerRedirectForProvisionalLoadForFrameFunc didReceiveServerRedirectForProvisionalLoadForFrameFunc;
-    WebDidCancelClientRedirectForFrameFunc didCancelClientRedirectForFrameFunc;
-    WebWillPerformClientRedirectToURLDelayFireDateForFrameFunc willPerformClientRedirectToURLDelayFireDateForFrameFunc;
-    WebDidChangeLocationWithinPageForFrameFunc didChangeLocationWithinPageForFrameFunc;
-    WebWillCloseFrameFunc willCloseFrameFunc;
-    WebDidStartProvisionalLoadForFrameFunc didStartProvisionalLoadForFrameFunc;
-    WebDidReceiveTitleForFrameFunc didReceiveTitleForFrameFunc;
-    WebDidCommitLoadForFrameFunc didCommitLoadForFrameFunc;
-    WebDidFailProvisionalLoadWithErrorForFrameFunc didFailProvisionalLoadWithErrorForFrameFunc;
-    WebDidFailLoadWithErrorForFrameFunc didFailLoadWithErrorForFrameFunc;
-    WebDidFinishLoadForFrameFunc didFinishLoadForFrameFunc;
-    WebDidFirstLayoutInFrameFunc didFirstLayoutInFrameFunc;
-    WebDidReceiveIconForFrameFunc didReceiveIconForFrameFunc;
-    WebDidFinishDocumentLoadForFrameFunc didFinishDocumentLoadForFrameFunc;
-} WebFrameLoadDelegateImplementationCache;
-
 extern NSString *_WebCanGoBackKey;
 extern NSString *_WebCanGoForwardKey;
 extern NSString *_WebEstimatedProgressKey;
@@ -334,6 +243,9 @@
 + (void)_setShouldUseFontSmoothing:(BOOL)f;
 + (BOOL)_shouldUseFontSmoothing;
 
+- (void)_setCatchesDelegateExceptions:(BOOL)f;
+- (BOOL)_catchesDelegateExceptions;
+
 // These two methods are useful for a test harness that needs a consistent appearance for the focus rings
 // regardless of OS X version.
 + (void)_setUsesTestModeFocusRingColor:(BOOL)f;
@@ -461,16 +373,6 @@
 - (void)_replaceSelectionWithNode:(DOMNode *)node matchStyle:(BOOL)matchStyle;
 @end
 
-@interface _WebSafeForwarder : NSObject
-{
-    id target; // Non-retained. Don't retain delegates.
-    id defaultTarget;
-    Class templateClass;
-}
-- (id)initWithTarget:(id)t defaultTarget:(id)dt templateClass:(Class)aClass;
-+ (id)safeForwarderWithTarget:(id)t defaultTarget:(id)dt templateClass:(Class)aClass;
-@end
-
 @interface NSObject (WebFrameLoadDelegatePrivate)
 - (void)webView:(WebView *)sender didFirstLayoutInFrame:(WebFrame *)frame;