/*
 * Copyright (C) 2005, 2006 Apple Computer, Inc.  All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * 1.  Redistributions of source code must retain the above copyright
 *     notice, this list of conditions and the following disclaimer. 
 * 2.  Redistributions in binary form must reproduce the above copyright
 *     notice, this list of conditions and the following disclaimer in the
 *     documentation and/or other materials provided with the distribution. 
 * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
 *     its contributors may be used to endorse or promote products derived
 *     from this software without specific prior written permission. 
 *
 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */


#import "WebPluginController.h"

#import "DOMNodeInternal.h"
#import "WebDataSourceInternal.h"
#import "WebFrameInternal.h"
#import "WebFrameView.h"
#import "WebHTMLViewPrivate.h"
#import "WebKitErrorsPrivate.h"
#import "WebKitLogging.h"
#import "WebNSObjectExtras.h"
#import "WebNSURLExtras.h"
#import "WebNSViewExtras.h"
#import "WebPlugin.h"
#import "WebPluginContainer.h"
#import "WebPluginContainerCheck.h"
#import "WebPluginPackage.h"
#import "WebPluginPrivate.h"
#import "WebPluginViewFactory.h"
#import "WebUIDelegate.h"
#import "WebViewInternal.h"
#import <Foundation/NSURLRequest.h>
#import <WebCore/DocumentLoader.h>
#import <WebCore/Frame.h>
#import <WebCore/FrameLoader.h>
#import <WebCore/HTMLMediaElement.h>
#import <WebCore/HTMLNames.h>
#import <WebCore/MediaPlayerProxy.h>
#import <WebCore/PlatformString.h>
#import <WebCore/ResourceRequest.h>
#import <WebCore/ScriptController.h>
#import <WebCore/WebCoreURLResponse.h>
#import <objc/objc-runtime.h>
#import <runtime/JSLock.h>

using namespace WebCore;
using namespace HTMLNames;

@interface NSView (PluginSecrets)
- (void)setContainingWindow:(NSWindow *)w;
@end

// For compatibility only.
@interface NSObject (OldPluginAPI)
+ (NSView *)pluginViewWithArguments:(NSDictionary *)arguments;
@end

@interface NSView (OldPluginAPI)
- (void)pluginInitialize;
- (void)pluginStart;
- (void)pluginStop;
- (void)pluginDestroy;
@end

static bool isKindOfClass(id, NSString* className);
static void installFlip4MacPlugInWorkaroundIfNecessary();


static NSMutableSet *pluginViews = nil;

@implementation WebPluginController

+ (NSView *)plugInViewWithArguments:(NSDictionary *)arguments fromPluginPackage:(WebPluginPackage *)pluginPackage
{
    [pluginPackage load];
    Class viewFactory = [pluginPackage viewFactory];
    
    NSView *view = nil;

    if ([viewFactory respondsToSelector:@selector(plugInViewWithArguments:)]) {
        JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
        view = [viewFactory plugInViewWithArguments:arguments];
    } else if ([viewFactory respondsToSelector:@selector(pluginViewWithArguments:)]) {
        JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
        view = [viewFactory pluginViewWithArguments:arguments];
    }
    
    if (view == nil) {
        return nil;
    }
    
    if (pluginViews == nil) {
        pluginViews = [[NSMutableSet alloc] init];
    }
    [pluginViews addObject:view];
    
    return view;
}

+ (BOOL)isPlugInView:(NSView *)view
{
    return [pluginViews containsObject:view];
}

- (id)initWithDocumentView:(NSView *)view
{
    [super init];
    _documentView = view;
    _views = [[NSMutableArray alloc] init];
    _checksInProgress = (NSMutableSet *)CFMakeCollectable(CFSetCreateMutable(NULL, 0, NULL));
    return self;
}

- (void)setDataSource:(WebDataSource *)dataSource
{
    _dataSource = dataSource;    
}

- (void)dealloc
{
    [_views release];
    [_checksInProgress release];
#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
    [_viewsNotInDocument release];
#endif
    [super dealloc];
}

- (void)stopOnePlugin:(NSView *)view
{
    if ([view respondsToSelector:@selector(webPlugInStop)]) {
        JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
        [view webPlugInStop];
    } else if ([view respondsToSelector:@selector(pluginStop)]) {
        JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
        [view pluginStop];
    }
}

- (void)destroyOnePlugin:(NSView *)view
{
    if ([view respondsToSelector:@selector(webPlugInDestroy)]) {
        JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
        [view webPlugInDestroy];
    } else if ([view respondsToSelector:@selector(pluginDestroy)]) {
        JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
        [view pluginDestroy];
    }
}

- (void)startAllPlugins
{
    if (_started)
        return;
    
    if ([_views count] > 0)
        LOG(Plugins, "starting WebKit plugins : %@", [_views description]);
    
    int count = [_views count];
    for (int i = 0; i < count; i++) {
        id aView = [_views objectAtIndex:i];
        if ([aView respondsToSelector:@selector(webPlugInStart)]) {
            JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
            [aView webPlugInStart];
        } else if ([aView respondsToSelector:@selector(pluginStart)]) {
            JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
            [aView pluginStart];
        }
    }
    _started = YES;
}

- (void)stopAllPlugins
{
    if (!_started)
        return;

    if ([_views count] > 0) {
        LOG(Plugins, "stopping WebKit plugins: %@", [_views description]);
    }
    
    int viewsCount = [_views count];
    for (int i = 0; i < viewsCount; i++)
        [self stopOnePlugin:[_views objectAtIndex:i]];

#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
    int viewsNotInDocumentCount = [_viewsNotInDocument count];
    for (int i = 0; i < viewsNotInDocumentCount; i++)
        [self stopOnePlugin:[_viewsNotInDocument objectAtIndex:i]];
#endif

    _started = NO;
}

#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
- (void)pluginViewCreated:(NSView *)view
{
    if (!_viewsNotInDocument)
        _viewsNotInDocument= [[NSMutableArray alloc] init];
    if (![_viewsNotInDocument containsObject:view])
        [_viewsNotInDocument addObject:view];
}

+ (void)pluginViewHidden:(NSView *)view
{
    [pluginViews removeObject:view];
}
#endif

- (void)addPlugin:(NSView *)view
{
    if (!_documentView) {
        LOG_ERROR("can't add a plug-in to a defunct WebPluginController");
        return;
    }
    
    if (![_views containsObject:view]) {
        [_views addObject:view];
        [[_documentView _webView] addPluginInstanceView:view];

#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
        if ([_viewsNotInDocument containsObject:view])
            [_viewsNotInDocument removeObject:view];
#endif

        BOOL oldDefersCallbacks = [[self webView] defersCallbacks];
        if (!oldDefersCallbacks)
            [[self webView] setDefersCallbacks:YES];

        if (isKindOfClass(view, @"WmvPlugin"))
            installFlip4MacPlugInWorkaroundIfNecessary();

        LOG(Plugins, "initializing plug-in %@", view);
        if ([view respondsToSelector:@selector(webPlugInInitialize)]) {
            JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
            [view webPlugInInitialize];
        } else if ([view respondsToSelector:@selector(pluginInitialize)]) {
            JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
            [view pluginInitialize];
        }

        if (!oldDefersCallbacks)
            [[self webView] setDefersCallbacks:NO];
        
        if (_started) {
            LOG(Plugins, "starting plug-in %@", view);
            if ([view respondsToSelector:@selector(webPlugInStart)]) {
                JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
                [view webPlugInStart];
            } else if ([view respondsToSelector:@selector(pluginStart)]) {
                JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
                [view pluginStart];
            }
            
            if ([view respondsToSelector:@selector(setContainingWindow:)]) {
                JSC::JSLock::DropAllLocks dropAllLocks(JSC::SilenceAssertionsOnly);
                [view setContainingWindow:[_documentView window]];
            }
        }
    }
}

- (void)destroyPlugin:(NSView *)view
{
#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
    if ([_views containsObject:view] || [_viewsNotInDocument containsObject:view]) {
#else
    if ([_views containsObject:view]) {
#endif
        if (_started)
            [self stopOnePlugin:view];
        [self destroyOnePlugin:view];
        
#if ENABLE(NETSCAPE_PLUGIN_API)
        if (Frame* frame = core([self webFrame]))
            frame->script()->cleanupScriptObjectsForPlugin(self);
#endif
        
        [pluginViews removeObject:view];
        [[_documentView _webView] removePluginInstanceView:view];
        [_views removeObject:view];
#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
        [_viewsNotInDocument removeObject:view];
#endif
    }
}

- (void)_webPluginContainerCancelCheckIfAllowedToLoadRequest:(id)checkIdentifier
{
    [checkIdentifier cancel];
    [_checksInProgress removeObject:checkIdentifier];
}

static void cancelOutstandingCheck(const void *item, void *context)
{
    [(id)item cancel];
}

- (void)_cancelOutstandingChecks
{
    if (_checksInProgress) {
        CFSetApplyFunction((CFSetRef)_checksInProgress, cancelOutstandingCheck, NULL);
        [_checksInProgress release];
        _checksInProgress = nil;
    }
}

- (void)destroyAllPlugins
{    
    [self stopAllPlugins];

    if ([_views count] > 0) {
        LOG(Plugins, "destroying WebKit plugins: %@", [_views description]);
    }

    [self _cancelOutstandingChecks];
    
    int viewsCount = [_views count];
    for (int i = 0; i < viewsCount; i++) {
        id aView = [_views objectAtIndex:i];
        [self destroyOnePlugin:aView];
        
#if ENABLE(NETSCAPE_PLUGIN_API)
        if (Frame* frame = core([self webFrame]))
            frame->script()->cleanupScriptObjectsForPlugin(self);
#endif
        
        [pluginViews removeObject:aView];
        [[_documentView _webView] removePluginInstanceView:aView];
    }

#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
    int viewsNotInDocumentCount = [_viewsNotInDocument count];
    for (int i = 0; i < viewsNotInDocumentCount; i++)
        [self destroyOnePlugin:[_viewsNotInDocument objectAtIndex:i]];
#endif

    [_views makeObjectsPerformSelector:@selector(removeFromSuperviewWithoutNeedingDisplay)];
    [_views release];
    _views = nil;

    _documentView = nil;
}

- (id)_webPluginContainerCheckIfAllowedToLoadRequest:(NSURLRequest *)request inFrame:(NSString *)target resultObject:(id)obj selector:(SEL)selector
{
    WebPluginContainerCheck *check = [WebPluginContainerCheck checkWithRequest:request target:target resultObject:obj selector:selector controller:self contextInfo:nil];
    [_checksInProgress addObject:check];
    [check start];

    return check;
}

- (void)webPlugInContainerLoadRequest:(NSURLRequest *)request inFrame:(NSString *)target
{
    if (!request) {
        LOG_ERROR("nil URL passed");
        return;
    }
    if (!_documentView) {
        LOG_ERROR("could not load URL %@ because plug-in has already been destroyed", request);
        return;
    }
    WebFrame *frame = [_dataSource webFrame];
    if (!frame) {
        LOG_ERROR("could not load URL %@ because plug-in has already been stopped", request);
        return;
    }
    if (!target) {
        target = @"_top";
    }
    NSString *JSString = [[request URL] _webkit_scriptIfJavaScriptURL];
    if (JSString) {
        if ([frame findFrameNamed:target] != frame) {
            LOG_ERROR("JavaScript requests can only be made on the frame that contains the plug-in");
            return;
        }
        [frame _stringByEvaluatingJavaScriptFromString:JSString];
    } else {
        if (!request) {
            LOG_ERROR("could not load URL %@", [request URL]);
            return;
        }
        core(frame)->loader()->load(request, target, false);
    }
}

- (void)webPlugInContainerShowStatus:(NSString *)message
{
    if (!message)
        message = @"";

    WebView *v = [_dataSource _webView];
    [[v _UIDelegateForwarder] webView:v setStatusText:message];
}

// For compatibility only.
- (void)showStatus:(NSString *)message
{
    [self webPlugInContainerShowStatus:message];
}

- (NSColor *)webPlugInContainerSelectionColor
{
    bool primary = true;
    if (Frame* frame = core([self webFrame]))
        primary = frame->selection()->isFocusedAndActive();
    return primary ? [NSColor selectedTextBackgroundColor] : [NSColor secondarySelectedControlColor];
}

// For compatibility only.
- (NSColor *)selectionColor
{
    return [self webPlugInContainerSelectionColor];
}

- (WebFrame *)webFrame
{
    return [_dataSource webFrame];
}

- (WebView *)webView
{
    return [[self webFrame] webView];
}

- (NSString *)URLPolicyCheckReferrer
{
    NSURL *responseURL = [[[[self webFrame] _dataSource] response] URL];
    ASSERT(responseURL);
    return [responseURL _web_originalDataAsString];
}

- (void)pluginView:(NSView *)pluginView receivedResponse:(NSURLResponse *)response
{    
    if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidReceiveResponse:)])
        [pluginView webPlugInMainResourceDidReceiveResponse:response];
    else {
        // Cancel the load since this plug-in does its own loading.
        // FIXME: See <rdar://problem/4258008> for a problem with this.
        NSError *error = [[NSError alloc] _initWithPluginErrorCode:WebKitErrorPlugInWillHandleLoad
                                                        contentURL:[response URL]
                                                     pluginPageURL:nil
                                                        pluginName:nil // FIXME: Get this from somewhere
                                                          MIMEType:[response MIMEType]];
        [_dataSource _documentLoader]->cancelMainResourceLoad(error);
        [error release];
    }        
}

- (void)pluginView:(NSView *)pluginView receivedData:(NSData *)data
{
    if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidReceiveData:)])
        [pluginView webPlugInMainResourceDidReceiveData:data];
}

- (void)pluginView:(NSView *)pluginView receivedError:(NSError *)error
{
    if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidFailWithError:)])
        [pluginView webPlugInMainResourceDidFailWithError:error];
}

- (void)pluginViewFinishedLoading:(NSView *)pluginView
{
    if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidFinishLoading)])
        [pluginView webPlugInMainResourceDidFinishLoading];
}

#if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
static WebCore::HTMLMediaElement* mediaProxyClient(DOMElement* element)
{
    if (!element) {
        LOG_ERROR("nil element passed");
        return nil;
    }

    Element* node = core(element);
    if (!node || (!node->hasTagName(HTMLNames::videoTag) && !node->hasTagName(HTMLNames::audioTag))) {
        LOG_ERROR("invalid media element passed");
        return nil;
    }

    return static_cast<WebCore::HTMLMediaElement*>(node);
}

- (void)_webPluginContainerSetMediaPlayerProxy:(WebMediaPlayerProxy *)proxy forElement:(DOMElement *)element
{
    WebCore::HTMLMediaElement* client = mediaProxyClient(element);
    if (client)
        client->setMediaPlayerProxy(proxy);
}

- (void)_webPluginContainerPostMediaPlayerNotification:(int)notification forElement:(DOMElement *)element
{
    WebCore::HTMLMediaElement* client = mediaProxyClient(element);
    if (client)
        client->deliverNotification((MediaPlayerProxyNotificationType)notification);
}
#endif

@end

static bool isKindOfClass(id object, NSString *className)
{
    Class cls = NSClassFromString(className);

    if (!cls)
        return false;

    return [object isKindOfClass:cls];
}


// Existing versions of the Flip4Mac WebKit plug-in have an object lifetime bug related to an NSAlert that is
// used to notify the user about updates to the plug-in. This bug can result in Safari crashing if the page
// containing the plug-in navigates while the alert is displayed (<rdar://problem/7313430>).
//
// The gist of the bug is thus: Flip4Mac sets an instance of the TSUpdateCheck class as the modal delegate of the
// NSAlert instance. This TSUpdateCheck instance itself has a delegate. The delegate is set to the WmvPlugin
// instance which is the NSView subclass that is exposed to WebKit as the plug-in view. Since this relationship
// is that of delegates the TSUpdateCheck does not retain the WmvPlugin. This leads to a bug if the WmvPlugin
// instance is destroyed before the TSUpdateCheck instance as the TSUpdateCheck instance will be left with a
// pointer to a stale object. This will happen if a page containing the Flip4Mac plug-in triggers a navigation
// while the update sheet is visible as the WmvPlugin instance is removed from the view hierarchy and there are
// no other references to keep the object alive.
//
// We work around this bug by patching the following two messages:
//
// 1) -[NSAlert beginSheetModalForWindow:modalDelegate:didEndSelector:contextInfo:]
// 2) -[TSUpdateCheck alertDidEnd:returnCode:contextInfo:]
//
// Our override of 1) detects whether it is Flip4Mac's update sheet triggering the alert by checking whether the
// modal delegate is an instance of TSUpdateCheck. If it is, it retains the modal delegate's delegate.
//
// Our override of 2) then autoreleases the delegate, balancing the retain we added in 1).
//
// These two overrides have the effect of ensuring that the WmvPlugin instance will always outlive the TSUpdateCheck
// instance, preventing the TSUpdateCheck instance from accessing a stale delegate pointer and crashing the application.


typedef void (*beginSheetModalForWindowIMP)(id, SEL, NSWindow *, id, SEL, void*);
static beginSheetModalForWindowIMP original_NSAlert_beginSheetModalForWindow_modalDelegate_didEndSelector_contextInfo_;

typedef void (*alertDidEndIMP)(id, SEL, NSAlert *, NSInteger, void*);
static alertDidEndIMP original_TSUpdateCheck_alertDidEnd_returnCode_contextInfo_;

static void WebKit_TSUpdateCheck_alertDidEnd_returnCode_contextInfo_(id object, SEL selector, NSAlert *alert, NSInteger returnCode, void* contextInfo)
{
    [[object delegate] autorelease];

    original_TSUpdateCheck_alertDidEnd_returnCode_contextInfo_(object, selector, alert, returnCode, contextInfo);
}

static void WebKit_NSAlert_beginSheetModalForWindow_modalDelegate_didEndSelector_contextInfo_(id object, SEL selector, NSWindow *window, id modalDelegate, SEL didEndSelector, void* contextInfo)
{
    if (isKindOfClass(modalDelegate, @"TSUpdateCheck"))
        [[modalDelegate delegate] retain];

    original_NSAlert_beginSheetModalForWindow_modalDelegate_didEndSelector_contextInfo_(object, selector, window, modalDelegate, didEndSelector, contextInfo);
}

static void installFlip4MacPlugInWorkaroundIfNecessary()
{
    static bool hasInstalledFlip4MacPlugInWorkaround;
    if (!hasInstalledFlip4MacPlugInWorkaround) {
        Class TSUpdateCheck = objc_lookUpClass("TSUpdateCheck");
        if (!TSUpdateCheck)
            return;

        Method methodToPatch = class_getInstanceMethod(TSUpdateCheck, @selector(alertDidEnd:returnCode:contextInfo:));
        if (!methodToPatch)
            return;

        IMP originalMethod = method_setImplementation(methodToPatch, reinterpret_cast<IMP>(WebKit_TSUpdateCheck_alertDidEnd_returnCode_contextInfo_));
        original_TSUpdateCheck_alertDidEnd_returnCode_contextInfo_ = reinterpret_cast<alertDidEndIMP>(originalMethod);

        methodToPatch = class_getInstanceMethod(objc_getRequiredClass("NSAlert"), @selector(beginSheetModalForWindow:modalDelegate:didEndSelector:contextInfo:));
        originalMethod = method_setImplementation(methodToPatch, reinterpret_cast<IMP>(WebKit_NSAlert_beginSheetModalForWindow_modalDelegate_didEndSelector_contextInfo_));
        original_NSAlert_beginSheetModalForWindow_modalDelegate_didEndSelector_contextInfo_ = reinterpret_cast<beginSheetModalForWindowIMP>(originalMethod);

        hasInstalledFlip4MacPlugInWorkaround = true;
    }
}
