/*
 * Copyright 2007 Google Inc.
 * 
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
 * use this file except in compliance with the License. You may obtain a copy of
 * the License at
 * 
 * http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
 * License for the specific language governing permissions and limitations under
 * the License.
 */

/*
 * Defines the JavaScript class gwt_external_class, which interface via JNI
 * to Java objects.
 */

#include <jni.h>
#include "JsRootedValue.h"
#include "gwt-jni.h"
#include "ExternalWrapper.h"
#include "Tracer.h"
#include "JsStringWrap.h"

// note that this does not use the NS_DEFINE_CID macro because it defines
// the variable as const, which by default has internal linkage.  I could
// work around it by putting extern in front of the macro, but that seems
// fragile if the macro changes.
nsCID kGwtExternalCID = GWT_EXTERNAL_FACTORY_CID;

/*
 * definition of JavaScript gwtOnLoad method which maps to the Java
 * gwtOnLoad method.
 */
static JSBool gwtOnLoad(JSContext *cx, JSObject *obj, uintN argc,
    jsval *argv, jsval *rval)
{
  Tracer tracer("gwtOnLoad");
  if (argc < 2) {
    tracer.setFail("less than 2 args");
    return JS_FALSE;
  }

  JSObject* scriptWindow = 0;
  if (argv[0] != JSVAL_NULL && argv[0] != JSVAL_VOID) {
    if (!JS_ValueToObject(cx, argv[0], &scriptWindow)) {
      tracer.setFail("can't get script window object");
      return JS_FALSE;
    }
  }

  JSString* moduleName = 0;
  if (argv[1] != JSVAL_NULL && argv[1] != JSVAL_VOID) {
    moduleName = JS_ValueToString(cx, argv[1]);
  }

  nsCOMPtr<nsIScriptGlobalObject> scriptGlobal(0);
  if (scriptWindow) {
    nsCOMPtr<nsIXPConnect> xpConnect = do_GetService(nsIXPConnect::GetCID());
    nsCOMPtr<nsIXPConnectWrappedNative> wrappedNative;
    xpConnect->GetWrappedNativeOfJSObject(cx, scriptWindow,
        getter_AddRefs(wrappedNative));
    if (wrappedNative) {
        nsCOMPtr<nsISupports> native;
        wrappedNative->GetNative(getter_AddRefs(native));
        scriptGlobal = do_QueryInterface(native);
    }
  }
  jstring jModuleName(0);
  if (moduleName) {
    jModuleName = savedJNIEnv->NewString(JS_GetStringChars(moduleName),
        JS_GetStringLength(moduleName));
    if (!jModuleName || savedJNIEnv->ExceptionCheck()) {
      tracer.setFail("can't get module name in Java string");
      return JS_FALSE;
    }
  }
  
  jobject externalObject = NS_REINTERPRET_CAST(jobject, JS_GetPrivate(cx, obj));
  jclass objClass = savedJNIEnv->GetObjectClass(externalObject);
  if (!objClass || savedJNIEnv->ExceptionCheck()) {
    tracer.setFail("can't get LowLevelMoz.ExternalObject class");
    return JS_FALSE;
  }
  
  jmethodID methodID = savedJNIEnv->GetMethodID(objClass, "gwtOnLoad",
      "(ILjava/lang/String;)Z");
  if (!methodID || savedJNIEnv->ExceptionCheck()) {
    tracer.setFail("can't get gwtOnLoad method");
    return JS_FALSE;
  }
  
  jboolean result = savedJNIEnv->CallBooleanMethod(externalObject, methodID,
      NS_REINTERPRET_CAST(jint, scriptGlobal.get()), jModuleName);
  if (savedJNIEnv->ExceptionCheck()) {
    tracer.setFail("LowLevelMoz.ExternalObject.gwtOnLoad() threw an exception");
    return JS_FALSE;
  }
  *rval = BOOLEAN_TO_JSVAL((result == JNI_FALSE) ? JS_FALSE : JS_TRUE);
  return JS_TRUE;
}

/*=======================================================================*/
/* Implementation of the getProperty, setProperty, and finalize methods  */
/* for the JavaScript class gwt_external_class.                          */
/*=======================================================================*/

static JSBool JS_DLL_CALLBACK gwt_external_getProperty(JSContext *cx,
    JSObject *obj, jsval id, jsval *vp)
{
  Tracer tracer("gwt_external_getProperty");
  if (*vp != JSVAL_VOID)
    return JS_TRUE;

  if (!JSVAL_IS_STRING(id)) {
    tracer.setFail("not a string");
    return JS_FALSE;
  }
  JsStringWrap jsStr(cx, id);
  tracer.log("obj=%08x, property=%.*s", obj, jsStr.length(), jsStr.bytes());

// All this is for calling resolveReference which only returns void.  So,
// just replace this code to return void for now.  TODO(jat): revisit when
// merging in Toby's code. 
#if 0
  jstring jident = savedJNIEnv->NewString(jsStr.chars(), jsStr.length());
  if (!jident || savedJNIEnv->ExceptionCheck()) {
    tracer.setFail("can't create Java string ");
    return JS_FALSE;
  }
  jobject externalObject = NS_REINTERPRET_CAST(jobject, JS_GetPrivate(cx, obj));
  jclass objClass = savedJNIEnv->GetObjectClass(externalObject);
  if (!objClass || savedJNIEnv->ExceptionCheck()) {
    tracer.setFail("can't find Java class for JS object");
    return JS_FALSE;
  }

  jmethodID methodID = savedJNIEnv->GetMethodID(objClass, "resolveReference",
      "(Ljava/lang/String;)I");
  if (!methodID || savedJNIEnv->ExceptionCheck()) {
    tracer.setFail("exception getting method for int resolveReference(String)");
    return JS_FALSE;
  }
  int retval = savedJNIEnv->CallIntMethod(externalObject, methodID, jident);
  if (savedJNIEnv->ExceptionCheck()) {
    tracer.setFail("exception calling int resolveReference(String)");
    return JS_FALSE;
  }
  *vp = retval;
#else
  *vp = JSVAL_VOID;
#endif
  return JS_TRUE;
}

static void JS_DLL_CALLBACK gwt_external_finalize(JSContext *cx, JSObject *obj)
{
  jobject externalObject = NS_REINTERPRET_CAST(jobject, JS_GetPrivate(cx, obj));
  if (externalObject)
    savedJNIEnv->DeleteGlobalRef(externalObject);
  JS_FinalizeStub(cx,obj);
}

static JSBool JS_DLL_CALLBACK gwt_external_setProperty(JSContext *cx,
    JSObject *obj, jsval id, jsval *vp)
{
  return JS_FALSE;
}
 
static JSClass gwt_external_class = {
    "gwt_external_class", JSCLASS_HAS_PRIVATE,
    JS_PropertyStub, JS_PropertyStub, gwt_external_getProperty,
    gwt_external_setProperty, JS_EnumerateStub, JS_ResolveStub, JS_ConvertStub,
    gwt_external_finalize,
    JSCLASS_NO_OPTIONAL_MEMBERS
};

NS_IMPL_ISUPPORTS1(ExternalWrapper, nsIScriptObjectOwner)

/*
 * Create a new LowLevelMoz.ExternalObject instance and a JavaScript object
 * that refers to it, mapping the gwtOnLoad member function mapping to
 * a Javascript method.
 */
NS_IMETHODIMP ExternalWrapper::GetScriptObject(nsIScriptContext *aContext,
    void** aScriptObject)
{
  Tracer tracer("ExternalWrapper::GetScriptObject"); 
  if (!aScriptObject) {
    tracer.setFail("null script object pointer");
    return NS_ERROR_INVALID_POINTER;
  }
  if (!mScriptObject) {
    *aScriptObject = 0;

    nsIScriptGlobalObject* globalObject = aContext->GetGlobalObject();
    nsCOMPtr<nsIDOMWindow> domWindow(do_QueryInterface(globalObject));
    if (!domWindow) {
      tracer.setFail("can't get DOM window");
      return NS_ERROR_UNEXPECTED;
    }
    nsCOMPtr<nsIDOMWindow> topWindow;
    domWindow->GetTop(getter_AddRefs(topWindow));
    if (!topWindow) {
      tracer.setFail("Can't get top window");
      return NS_ERROR_UNEXPECTED;
    }

    tracer.log("savedJNIEnv=%08x, llClass=%08x", unsigned(savedJNIEnv),
        lowLevelMozClass);
    
    jmethodID methodID = savedJNIEnv->GetStaticMethodID(lowLevelMozClass,
        "createExternalObjectForDOMWindow",
        "(I)Lcom/google/gwt/dev/shell/moz/LowLevelMoz$ExternalObject;");
    if (!methodID || savedJNIEnv->ExceptionCheck()) {
      tracer.setFail("Can't get createExternalObjectForDOMWindow method");
      return NS_ERROR_UNEXPECTED;
    }

    jobject externalObject = savedJNIEnv->CallStaticObjectMethod(
        lowLevelMozClass, methodID, NS_REINTERPRET_CAST(jint, topWindow.get()));
    if (!externalObject || savedJNIEnv->ExceptionCheck()) {
      tracer.setFail("createExternalObjectForDOMWindow failed");
      return NS_ERROR_UNEXPECTED;
    }
    externalObject = savedJNIEnv->NewGlobalRef(externalObject);
    if (!externalObject || savedJNIEnv->ExceptionCheck()) {
      tracer.setFail("can't get GlobalRef for external object");
      return NS_ERROR_UNEXPECTED;
    }
    JSContext* cx = NS_REINTERPRET_CAST(JSContext*,
        aContext->GetNativeContext());
    if (!cx) {
      tracer.setFail("can't get JSContext");
      return NS_ERROR_UNEXPECTED;
    }
    JSObject* newObj = JS_NewObject(cx, &gwt_external_class, 0,
        globalObject->GetGlobalJSObject());
    if (!newObj) {
      tracer.setFail("can't create new gwt_external_class object");
      return NS_ERROR_OUT_OF_MEMORY;
    }
    if (!JS_SetPrivate(cx, newObj, externalObject)) {
      savedJNIEnv->DeleteGlobalRef(externalObject);
      tracer.setFail("can't store external object private reference");
      return NS_ERROR_UNEXPECTED;
    }
  
    if (!JS_DefineFunction(cx, newObj, "gwtOnLoad", gwtOnLoad, 3,
        JSPROP_ENUMERATE | JSPROP_READONLY | JSPROP_PERMANENT)) {
      tracer.setFail("can't define gwtOnLoad function on JavaScript object");
      return NS_ERROR_UNEXPECTED;
    }
    mScriptObject = newObj;
  }

  *aScriptObject = mScriptObject;
  return NS_OK;
}

NS_IMETHODIMP ExternalWrapper::SetScriptObject(void* aScriptObject)
{
    mScriptObject = aScriptObject;
    return NS_OK;
}

NS_IMPL_ISUPPORTS1(nsRpExternalFactory, nsIFactory)

NS_IMETHODIMP nsRpExternalFactory::CreateInstance(nsISupports *aOuter,
    const nsIID& aIID, void** aResult)
{
  Tracer tracer("nsRpExternalFactory::CreateInstance");
  if (!aResult) {
    tracer.setFail("null pointer for return value");
    return NS_ERROR_INVALID_POINTER;
  }
  *aResult  = NULL;

  if (aOuter) {
    tracer.setFail("aOuter is not null");
    return NS_ERROR_NO_AGGREGATION;
  }

  nsISupports* object = new ExternalWrapper();
  if (!object) {
    tracer.setFail("can't create a new ExternalWrapper");
    return NS_ERROR_OUT_OF_MEMORY;
  }
      
  nsresult result = object->QueryInterface(aIID, aResult);
  if (!*aResult || NS_FAILED(result)) {
    tracer.setFail("ExternalWrapper::QueryInterface failed");
    delete object;
  }
  return result;
}

NS_IMETHODIMP nsRpExternalFactory::LockFactory(PRBool lock)
{
    return NS_ERROR_NOT_IMPLEMENTED;
}
