示例#1
0
static HRESULT RuntimeHost_GetIUnknownForDomain(RuntimeHost *This, MonoDomain *domain, IUnknown **punk)
{
    HRESULT hr;
    void *args[1];
    MonoAssembly *assembly;
    MonoImage *image;
    MonoClass *klass;
    MonoMethod *method;
    MonoObject *appdomain_object;
    IUnknown *unk;

    mono_thread_attach(domain);

    assembly = mono_domain_assembly_open(domain, "mscorlib");
    if (!assembly)
    {
        ERR("Cannot load mscorlib\n");
        return E_FAIL;
    }

    image = mono_assembly_get_image(assembly);
    if (!image)
    {
        ERR("Couldn't get assembly image\n");
        return E_FAIL;
    }

    klass = mono_class_from_name(image, "System", "AppDomain");
    if (!klass)
    {
        ERR("Couldn't get class from image\n");
        return E_FAIL;
    }

    method = mono_class_get_method_from_name(klass, "get_CurrentDomain", 0);
    if (!method)
    {
        ERR("Couldn't get method from class\n");
        return E_FAIL;
    }

    args[0] = NULL;
    appdomain_object = mono_runtime_invoke(method, NULL, args, NULL);
    if (!appdomain_object)
    {
        ERR("Couldn't get result pointer\n");
        return E_FAIL;
    }

    hr = RuntimeHost_GetIUnknownForObject(This, appdomain_object, &unk);

    if (SUCCEEDED(hr))
    {
        hr = IUnknown_QueryInterface(unk, &IID__AppDomain, (void**)punk);

        IUnknown_Release(unk);
    }

    return hr;
}
示例#2
0
文件: xmono.cpp 项目: 0bj3ct/xmono
static void lua_code_exec (Package *pkg) {
    static lua_State *L = 0;
    xmono::LuaExecRsp rsp;
    xmono::LuaExecReq req;
    MonoThread *thread = mono_thread_attach (mono_domain_get_by_id (0));
    do {
        if (L == 0 && !(L = lua_env_new ())) {
            rsp.set_level (xmono::LuaExecRsp::err);
            rsp.set_message ("create a lua_State err.");
            break;
        }
        std::string str((char*)pkg->body, pkg->all_len - sizeof (Package)); //Fixme : 修复头部all_len是总长的问题
        if (!req.ParseFromString (str)) {
            LOGD ("xmono::LuaExecReq ParseFromString err!");
            return;
        }
        if (luaL_dostring (L, req.lua_code ().c_str ())) {
            rsp.set_level (xmono::LuaExecRsp::err);
            rsp.set_message (lua_tostring (L, -1));
            break;
        }
        rsp.set_level (xmono::LuaExecRsp::debug);
        rsp.set_message ("exec the lua string ok.");
    } while (0);
    mono_thread_detach (thread);
    std::string out;
    rsp.SerializeToString (&out);
    ecmd_send (XMONO_ID_LUA_EXEC_RSP, (uint8_t const*)out.c_str (), out.size ());
    return;
}
示例#3
0
	MonoAttachment()
		: thread(nullptr)
	{
		if (!mono_domain_get())
		{
			thread = mono_thread_attach(g_rootDomain);
		}
	}
示例#4
0
static MonoDomain* domain_attach(MonoDomain *domain)
{
    MonoDomain *prev_domain = mono_domain_get();

    if (prev_domain == domain)
        /* Do not set or restore domain. */
        return NULL;

    mono_thread_attach(domain);

    return prev_domain;
}
示例#5
0
void RuntimeHost_ExitProcess(RuntimeHost *This, INT exitcode)
{
    HRESULT hr;
    void *args[2];
    MonoDomain *domain;
    MonoAssembly *assembly;
    MonoImage *image;
    MonoClass *klass;
    MonoMethod *method;

    hr = RuntimeHost_GetDefaultDomain(This, &domain);
    if (FAILED(hr))
    {
        ERR("Cannot get domain, hr=%x\n", hr);
        return;
    }

    mono_thread_attach(domain);

    assembly = mono_domain_assembly_open(domain, "mscorlib");
    if (!assembly)
    {
        ERR("Cannot load mscorlib\n");
        return;
    }

    image = mono_assembly_get_image(assembly);
    if (!image)
    {
        ERR("Couldn't get assembly image\n");
        return;
    }

    klass = mono_class_from_name(image, "System", "Environment");
    if (!klass)
    {
        ERR("Couldn't get class from image\n");
        return;
    }

    method = mono_class_get_method_from_name(klass, "Exit", 1);
    if (!method)
    {
        ERR("Couldn't get method from class\n");
        return;
    }

    args[0] = &exitcode;
    args[1] = NULL;
    mono_runtime_invoke(method, NULL, args, NULL);

    ERR("Process should have exited\n");
}
示例#6
0
static MonoThread *
get_mono_thread ()
{
#ifndef MONO_AGENT
  thread_t *thr = THREAD_CURRENT_THREAD;
  MonoThread *ret_thr = NULL;
  if (NULL == (ret_thr = (MonoThread *) THR_ATTR (thr, TA_MONO_THREAD)))
    {
      ret_thr = mono_thread_attach (virtuoso_domain);
      SET_THR_ATTR (thr, TA_MONO_THREAD, ret_thr);
    }
  return ret_thr;
#else
  return NULL;
#endif
}
示例#7
0
void attach_current_thread() {
	ERR_FAIL_COND(!GDMono::get_singleton()->is_runtime_initialized());
	MonoThread *mono_thread = mono_thread_attach(SCRIPTS_DOMAIN);
	ERR_FAIL_NULL(mono_thread);
}
示例#8
0
MonoDomain* JniManager::getMonoDomain()
{
    MonoDomain* monoDomain = mono_get_root_domain();
    mono_thread_attach(monoDomain);
    return monoDomain;
}
示例#9
0
bool VdsViewEventHandler::handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& us)
{
	if (!_eventClass)
		return false;
	int x = ea.getX();
	int y = ea.getY();
	MonoImage* monoImage = NULL;
	MonoClass* eventClass = NULL;
	MonoObject* eventClassObject = NULL;
	MonoMethod*	mousePushMethod = NULL;
	MonoMethod*	mouseReleaseMethod = NULL;
	MonoMethod*	mouseMoveMethod = NULL;
	MonoMethod*	mouseDoubleClickMethod = NULL;
	MonoMethod*	mouseZoomMethod = NULL;
	MonoMethod*	keyDownMethod = NULL;
	MonoMethod*	keyUpMethod = NULL;
	MonoMethod*	layerInSceneChangedMethod = NULL;
	MonoMethod*	gameManagerAddActorEventMethod = NULL;
	MonoMethod*	gameManagerRemoveActorEventMethod = NULL;
	MonoMethod*	gameManagerPlayPlotEventMethod = NULL;
	MonoMethod*	gameManagerStopPlotEventMethod = NULL;
	MonoMethod*	gameManagerPausePlotEventMethod = NULL;
	MonoMethod*	uiEventMethod = NULL;
	{
		OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_pMutex);
		monoImage = _monoImage;
		eventClass = _eventClass;
		eventClassObject = _eventClassObject;
		mousePushMethod = _mousePushMethod;
		mouseReleaseMethod = _mouseReleaseMethod;
		mouseMoveMethod = _mouseMoveMethod;
		mouseDoubleClickMethod = _mouseDoubleClickMethod;
		mouseZoomMethod = _mouseZoomMethod;
		keyDownMethod = _keyDownMethod;
		keyUpMethod = _keyUpMethod;
		layerInSceneChangedMethod = _layerInSceneChangedMethod;
		gameManagerAddActorEventMethod = _gameManagerAddActorEventMethod;
		gameManagerRemoveActorEventMethod = _gameManagerRemoveActorEventMethod;
		gameManagerPlayPlotEventMethod = _gameManagerPlayPlotEventMethod;
		gameManagerStopPlotEventMethod = _gameManagerStopPlotEventMethod;
		gameManagerPausePlotEventMethod = _gameManagerPausePlotEventMethod;
		uiEventMethod = _uiEventMethod;
	}
	switch (ea.getEventType())
	{
	case osgGA::GUIEventAdapter::MOVE:
	{
		if (!mouseMoveMethod)
			mouseMoveMethod = mono_class_get_method_from_name(eventClass, "MouseMoveEvent", 3);
		MonoObject* exception = NULL;
		void* args[3];
		args[0] = &_viewID;
		args[1] = &x;
		args[2] = &y;
		_eventThread = mono_thread_attach(mono_get_root_domain());
		mono_runtime_invoke(mouseMoveMethod, eventClassObject, args, &exception);
		break;
	}
	case osgGA::GUIEventAdapter::PUSH:
	{
		if (!mousePushMethod)
			mousePushMethod = mono_class_get_method_from_name(eventClass, "MouseButtonPressEvent", 4);
		MonoObject* exception = NULL;
		int arg0 = 1;
		void* args[4];
		args[0] = &_viewID;
		if (ea.getButton() == osgGA::GUIEventAdapter::LEFT_MOUSE_BUTTON)
			arg0 = 1;
		else if (ea.getButton() == osgGA::GUIEventAdapter::MIDDLE_MOUSE_BUTTON)
			arg0 = 2;
		else if (ea.getButton() == osgGA::GUIEventAdapter::RIGHT_MOUSE_BUTTON)
			arg0 = 3;
		args[1] = &arg0;
		args[2] = &x;
		args[3] = &y;
		_eventThread = mono_thread_attach(mono_get_root_domain());
		mono_runtime_invoke(mousePushMethod, eventClassObject, args, &exception);
		break;
	}
	case osgGA::GUIEventAdapter::RELEASE:
	{
		if (!mouseReleaseMethod)
			mouseReleaseMethod = mono_class_get_method_from_name(eventClass, "MouseButtonReleaseEvent", 4);
		MonoObject* exception = NULL;
		int arg0 = 1;
		void* args[4];
		args[0] = &_viewID;
		if (ea.getButton() == osgGA::GUIEventAdapter::LEFT_MOUSE_BUTTON)
			arg0 = 1;
		else if (ea.getButton() == osgGA::GUIEventAdapter::MIDDLE_MOUSE_BUTTON)
			arg0 = 2;
		else if (ea.getButton() == osgGA::GUIEventAdapter::RIGHT_MOUSE_BUTTON)
			arg0 = 3;
		args[1] = &arg0;
		args[2] = &x;
		args[3] = &y;
		_eventThread = mono_thread_attach(mono_get_root_domain());
		mono_runtime_invoke(mouseReleaseMethod, eventClassObject, args, &exception);
		break;
	}
	case osgGA::GUIEventAdapter::DOUBLECLICK:
	{
		if (!mouseDoubleClickMethod)
			mouseDoubleClickMethod = mono_class_get_method_from_name(eventClass, "MouseDoubleClickEvent", 4);
		MonoObject* exception = NULL;
		int arg0 = 1;
		void* args[4];
		args[0] = &_viewID;
		if (ea.getButton() == osgGA::GUIEventAdapter::LEFT_MOUSE_BUTTON)
			arg0 = 1;
		else if (ea.getButton() == osgGA::GUIEventAdapter::MIDDLE_MOUSE_BUTTON)
			arg0 = 2;
		else if (ea.getButton() == osgGA::GUIEventAdapter::RIGHT_MOUSE_BUTTON)
			arg0 = 3;
		args[1] = &arg0;
		args[2] = &x;
		args[3] = &y;
		_eventThread = mono_thread_attach(mono_get_root_domain());
		mono_runtime_invoke(mouseDoubleClickMethod, eventClassObject, args, &exception);
		break;
	}
	case osgGA::GUIEventAdapter::KEYDOWN:
	{
		if (!keyDownMethod)
			keyDownMethod = mono_class_get_method_from_name(eventClass, "KeyboardDownEvent", 2);
		MonoObject* exception = NULL;
		void* args[2];
		args[0] = &_viewID;
		int keyValue = ea.getKey();
		args[1] = &keyValue;
		_eventThread = mono_thread_attach(mono_get_root_domain());
		mono_runtime_invoke(keyDownMethod, eventClassObject, args, &exception);
		break;
	}
	case osgGA::GUIEventAdapter::KEYUP:
	{
		if (!keyUpMethod)
			keyUpMethod = mono_class_get_method_from_name(eventClass, "KeyboardUpEvent", 2);
		MonoObject* exception = NULL;
		void* args[2];
		args[0] = &_viewID;
		int keyValue = ea.getKey();
		args[1] = &keyValue;
		_eventThread = mono_thread_attach(mono_get_root_domain());
		mono_runtime_invoke(keyUpMethod, eventClassObject, args, &exception);
		break;
	}
	case osgGA::GUIEventAdapter::SCROLL:
	{
		if (!mouseZoomMethod)
			mouseZoomMethod = mono_class_get_method_from_name(eventClass, "MouseZoomEvent", 2);
		MonoObject* exception = NULL;
		void* args[2];
		args[0] = &_viewID;
		osgGA::GUIEventAdapter::ScrollingMotion sm = ea.getScrollingMotion();
		int zoomValue = 0;
		if (sm == osgGA::GUIEventAdapter::SCROLL_DOWN)
			zoomValue = 1;
		args[1] = &zoomValue;
		_eventThread = mono_thread_attach(mono_get_root_domain());
		mono_runtime_invoke(mouseZoomMethod, eventClassObject, args, &exception);
		break;
	}
	case osgGA::GUIEventAdapter::USER:
	{
		osg::ref_ptr<osg::Referenced> userData = const_cast<osg::Referenced*>(ea.getUserData());
		UserEventData* data = static_cast<UserEventData*>(userData.get());
		switch (data->_eventType)
		{
		case UserEventData::LAYERCHANGED:
		{
			if (!layerInSceneChangedMethod)
				layerInSceneChangedMethod = mono_class_get_method_from_name(eventClass, "LayerInSceneChangedEvent", 1);
			MonoObject* exception = NULL;
			void* args[1];
			args[0] = &_viewID;
			_eventThread = mono_thread_attach(mono_get_root_domain());
			mono_runtime_invoke(layerInSceneChangedMethod, eventClassObject, args, &exception);
			break;
		}
		case UserEventData::UI_EVENT:
		{
			if (!uiEventMethod)
				uiEventMethod = mono_class_get_method_from_name(eventClass, "UIEvent", 3);
			void* widthData = data->_data;
			std::vector<std::string>* dList = (std::vector<std::string>*)widthData;
			MonoDomain* domain = mono_object_get_domain(eventClassObject);
			MonoObject* exception = NULL;
			void* args[3];
			args[0] = &_viewID;
			args[1] = mono_string_new(domain, dList->at(0).c_str());
			args[2] = mono_string_new(domain, dList->at(1).c_str());
			_eventThread = mono_thread_attach(mono_get_root_domain());
			mono_runtime_invoke(uiEventMethod, eventClassObject, args, &exception);
			break;
		}
		case UserEventData::GAMEMANAGER_ACTORADD:
		{
			if (!gameManagerAddActorEventMethod)
				gameManagerAddActorEventMethod = mono_class_get_method_from_name(eventClass, "GameLayerAddActorEvent", 2);
			MonoDomain* domain = mono_object_get_domain(eventClassObject);
			MonoObject* exception = NULL;
			void* args[2];
			args[0] = &_viewID;
			args[1] = mono_string_new(domain, dynamic_cast<VirtualDataSceneBase::ActorBase*>(data->_eventObject.get())->getId().c_str());
			_eventThread = mono_thread_attach(mono_get_root_domain());
			mono_runtime_invoke(gameManagerAddActorEventMethod, eventClassObject, args, &exception);
			break;
		}
		case UserEventData::GAMEMANAGER_ACTORREMOVE:
		{
			if (!gameManagerRemoveActorEventMethod)
				gameManagerRemoveActorEventMethod = mono_class_get_method_from_name(eventClass, "GameLayerRemoveActorEvent", 2);
			MonoDomain* domain = mono_object_get_domain(eventClassObject);
			MonoObject* exception = NULL;
			void* args[2];
			args[0] = &_viewID;
			args[1] = mono_string_new(domain, dynamic_cast<VirtualDataSceneBase::ActorBase*>(data->_eventObject.get())->getId().c_str());
			_eventThread = mono_thread_attach(mono_get_root_domain());
			mono_runtime_invoke(gameManagerRemoveActorEventMethod, eventClassObject, args, &exception);
			break;
		}
		case UserEventData::GAMEMANAGER_PLAYPLOT:
		{
			if (!gameManagerPlayPlotEventMethod)
				gameManagerPlayPlotEventMethod = mono_class_get_method_from_name(eventClass, "PlayPlotScriptEvent", 3);
			void* widthData = data->_data;
			std::vector<std::string>* dList = (std::vector<std::string>*)widthData;
			MonoDomain* domain = mono_object_get_domain(eventClassObject);
			MonoObject* exception = NULL;
			void* args[3];
			args[0] = &_viewID;
			args[1] = mono_string_new(domain, dList->at(0).c_str());
			args[2] = mono_string_new(domain, dList->at(1).c_str());
			_eventThread = mono_thread_attach(mono_get_root_domain());
			mono_runtime_invoke(gameManagerPlayPlotEventMethod, eventClassObject, args, &exception);
			break;
		}
		case UserEventData::GAMEMANAGER_STOPPLOT:
		{
			if (!gameManagerStopPlotEventMethod)
				gameManagerStopPlotEventMethod = mono_class_get_method_from_name(eventClass, "StopPlotScriptEvent", 2);
			MonoDomain* domain = mono_object_get_domain(eventClassObject);
			MonoObject* exception = NULL;
			void* args[2];
			args[0] = &_viewID;
			args[1] = mono_string_new(domain, dynamic_cast<VirtualDataSceneBase::ActorBase*>(data->_eventObject.get())->getId().c_str());
			_eventThread = mono_thread_attach(mono_get_root_domain());
			mono_runtime_invoke(gameManagerStopPlotEventMethod, eventClassObject, args, &exception);
			break;
		}
		case UserEventData::GAMEMANAGER_PAUSEPLOT:
		{
			if (!gameManagerPausePlotEventMethod)
				gameManagerPausePlotEventMethod = mono_class_get_method_from_name(eventClass, "PausePlotScriptEvent", 2);
			MonoDomain* domain = mono_object_get_domain(eventClassObject);
			MonoObject* exception = NULL;
			void* args[2];
			args[0] = &_viewID;
			args[1] = mono_string_new(domain, dynamic_cast<VirtualDataSceneBase::ActorBase*>(data->_eventObject.get())->getId().c_str());
			_eventThread = mono_thread_attach(mono_get_root_domain());
			mono_runtime_invoke(gameManagerPausePlotEventMethod, eventClassObject, args, &exception);
			break;
		}
		default:
			break;
		}
		break;
	}
	case osgGA::GUIEventAdapter::CLOSE_WINDOW:
	case osgGA::GUIEventAdapter::QUIT_APPLICATION:
	{
		//mono_thread_detach(_eventThread);
		break;
	}
	default:
		break;
	}
	return false;
}
示例#10
0
static void CDECL ReallyFixupVTable(struct dll_fixup *fixup)
{
    HRESULT hr=S_OK;
    WCHAR filename[MAX_PATH];
    ICLRRuntimeInfo *info=NULL;
    RuntimeHost *host;
    char *filenameA;
    MonoImage *image=NULL;
    MonoAssembly *assembly=NULL;
    MonoImageOpenStatus status=0;
    MonoDomain *domain;

    if (fixup->done) return;

    /* It's possible we'll have two threads doing this at once. This is
     * considered preferable to the potential deadlock if we use a mutex. */

    GetModuleFileNameW(fixup->dll, filename, MAX_PATH);

    TRACE("%p,%p,%s\n", fixup, fixup->dll, debugstr_w(filename));

    filenameA = WtoA(filename);
    if (!filenameA)
        hr = E_OUTOFMEMORY;

    if (SUCCEEDED(hr))
        hr = get_runtime_info(filename, NULL, NULL, 0, 0, FALSE, &info);

    if (SUCCEEDED(hr))
        hr = ICLRRuntimeInfo_GetRuntimeHost(info, &host);

    if (SUCCEEDED(hr))
        hr = RuntimeHost_GetDefaultDomain(host, &domain);

    if (SUCCEEDED(hr))
    {
        mono_thread_attach(domain);

        assembly = mono_assembly_open(filenameA, &status);
    }

    if (assembly)
    {
        int i;

        /* Mono needs an image that belongs to an assembly. */
        image = mono_assembly_get_image(assembly);

        if (fixup->fixup->type & COR_VTABLE_32BIT)
        {
            DWORD *vtable = fixup->vtable;
            DWORD *tokens = fixup->tokens;
            for (i=0; i<fixup->fixup->count; i++)
            {
                TRACE("%x\n", tokens[i]);
                vtable[i] = PtrToUint(mono_marshal_get_vtfixup_ftnptr(
                    image, tokens[i], fixup->fixup->type));
            }
        }

        fixup->done = TRUE;
    }

    if (info != NULL)
        ICLRRuntimeInfo_Release(info);

    HeapFree(GetProcessHeap(), 0, filenameA);

    if (!fixup->done)
    {
        ERR("unable to fixup vtable, hr=%x, status=%d\n", hr, status);
        /* If we returned now, we'd get an infinite loop. */
        assert(0);
    }
}
示例#11
0
/* Create an instance of a type given its name, by calling its constructor with
 * no arguments. Note that result MUST be in the stack, or the garbage
 * collector may free it prematurely. */
HRESULT RuntimeHost_CreateManagedInstance(RuntimeHost *This, LPCWSTR name,
    MonoDomain *domain, MonoObject **result)
{
    HRESULT hr=S_OK;
    char *nameA=NULL;
    MonoType *type;
    MonoClass *klass;
    MonoObject *obj;

    if (!domain)
        hr = RuntimeHost_GetDefaultDomain(This, &domain);

    if (SUCCEEDED(hr))
    {
        nameA = WtoA(name);
        if (!nameA)
            hr = E_OUTOFMEMORY;
    }

    if (SUCCEEDED(hr))
    {
        mono_thread_attach(domain);

        type = mono_reflection_type_from_name(nameA, NULL);
        if (!type)
        {
            ERR("Cannot find type %s\n", debugstr_w(name));
            hr = E_FAIL;
        }
    }

    if (SUCCEEDED(hr))
    {
        klass = mono_class_from_mono_type(type);
        if (!klass)
        {
            ERR("Cannot convert type %s to a class\n", debugstr_w(name));
            hr = E_FAIL;
        }
    }

    if (SUCCEEDED(hr))
    {
        obj = mono_object_new(domain, klass);
        if (!obj)
        {
            ERR("Cannot allocate object of type %s\n", debugstr_w(name));
            hr = E_FAIL;
        }
    }

    if (SUCCEEDED(hr))
    {
        /* FIXME: Detect exceptions from the constructor? */
        mono_runtime_object_init(obj);
        *result = obj;
    }

    HeapFree(GetProcessHeap(), 0, nameA);

    return hr;
}
示例#12
0
static HRESULT WINAPI CLRRuntimeHost_ExecuteInDefaultAppDomain(ICLRRuntimeHost* iface,
    LPCWSTR pwzAssemblyPath, LPCWSTR pwzTypeName, LPCWSTR pwzMethodName,
    LPCWSTR pwzArgument, DWORD *pReturnValue)
{
    RuntimeHost *This = impl_from_ICLRRuntimeHost( iface );
    HRESULT hr;
    MonoDomain *domain;
    MonoAssembly *assembly;
    MonoImage *image;
    MonoClass *klass;
    MonoMethod *method;
    MonoObject *result;
    MonoString *str;
    void *args[2];
    char *filenameA = NULL, *classA = NULL, *methodA = NULL;
    char *argsA = NULL, *ns;

    TRACE("(%p,%s,%s,%s,%s)\n", iface, debugstr_w(pwzAssemblyPath),
        debugstr_w(pwzTypeName), debugstr_w(pwzMethodName), debugstr_w(pwzArgument));

    hr = RuntimeHost_GetDefaultDomain(This, &domain);
    if(hr != S_OK)
    {
        ERR("Couldn't get Default Domain\n");
        return hr;
    }

    hr = E_FAIL;

    mono_thread_attach(domain);

    filenameA = WtoA(pwzAssemblyPath);
    assembly = mono_domain_assembly_open(domain, filenameA);
    if (!assembly)
    {
        ERR("Cannot open assembly %s\n", filenameA);
        goto cleanup;
    }

    image = mono_assembly_get_image(assembly);
    if (!image)
    {
        ERR("Couldn't get assembly image\n");
        goto cleanup;
    }

    classA = WtoA(pwzTypeName);
    ns = strrchr(classA, '.');
    *ns = '\0';
    klass = mono_class_from_name(image, classA, ns+1);
    if (!klass)
    {
        ERR("Couldn't get class from image\n");
        goto cleanup;
    }

    methodA = WtoA(pwzMethodName);
    method = mono_class_get_method_from_name(klass, methodA, 1);
    if (!method)
    {
        ERR("Couldn't get method from class\n");
        goto cleanup;
    }

    /* The .NET function we are calling has the following declaration
     *   public static int functionName(String param)
     */
    argsA = WtoA(pwzArgument);
    str = mono_string_new(domain, argsA);
    args[0] = str;
    args[1] = NULL;
    result = mono_runtime_invoke(method, NULL, args, NULL);
    if (!result)
        ERR("Couldn't get result pointer\n");
    else
    {
        *pReturnValue = *(DWORD*)mono_object_unbox(result);
        hr = S_OK;
    }

cleanup:
    HeapFree(GetProcessHeap(), 0, filenameA);
    HeapFree(GetProcessHeap(), 0, classA);
    HeapFree(GetProcessHeap(), 0, argsA);
    HeapFree(GetProcessHeap(), 0, methodA);

    return hr;
}
示例#13
0
HRESULT create_monodata(REFIID riid, LPVOID *ppObj )
{
    static const WCHAR wszAssembly[] = {'A','s','s','e','m','b','l','y',0};
    static const WCHAR wszCodebase[] = {'C','o','d','e','B','a','s','e',0};
    static const WCHAR wszClass[] = {'C','l','a','s','s',0};
    static const WCHAR wszFileSlash[] = {'f','i','l','e',':','/','/','/',0};
    static const WCHAR wszCLSIDSlash[] = {'C','L','S','I','D','\\',0};
    static const WCHAR wszInprocServer32[] = {'\\','I','n','p','r','o','c','S','e','r','v','e','r','3','2',0};
    static const WCHAR wszDLL[] = {'.','d','l','l',0};
    WCHAR path[CHARS_IN_GUID + ARRAYSIZE(wszCLSIDSlash) + ARRAYSIZE(wszInprocServer32) - 1];
    MonoDomain *domain;
    MonoAssembly *assembly;
    ICLRRuntimeInfo *info = NULL;
    RuntimeHost *host;
    HRESULT hr;
    HKEY key, subkey;
    LONG res;
    int offset = 0;
    DWORD numKeys, keyLength;
    WCHAR codebase[MAX_PATH + 8];
    WCHAR classname[350], subkeyName[256];
    WCHAR filename[MAX_PATH];

    DWORD dwBufLen = 350;

    lstrcpyW(path, wszCLSIDSlash);
    StringFromGUID2(riid, path + lstrlenW(wszCLSIDSlash), CHARS_IN_GUID);
    lstrcatW(path, wszInprocServer32);

    TRACE("Registry key: %s\n", debugstr_w(path));

    res = RegOpenKeyExW(HKEY_CLASSES_ROOT, path, 0, KEY_READ, &key);
    if (res == ERROR_FILE_NOT_FOUND)
        return CLASS_E_CLASSNOTAVAILABLE;

    res = RegGetValueW( key, NULL, wszClass, RRF_RT_REG_SZ, NULL, classname, &dwBufLen);
    if(res != ERROR_SUCCESS)
    {
        WARN("Class value cannot be found.\n");
        hr = CLASS_E_CLASSNOTAVAILABLE;
        goto cleanup;
    }

    TRACE("classname (%s)\n", debugstr_w(classname));

    dwBufLen = MAX_PATH + 8;
    res = RegGetValueW( key, NULL, wszCodebase, RRF_RT_REG_SZ, NULL, codebase, &dwBufLen);
    if(res == ERROR_SUCCESS)
    {
        /* Strip file:/// */
        if(strncmpW(codebase, wszFileSlash, strlenW(wszFileSlash)) == 0)
            offset = strlenW(wszFileSlash);

        strcpyW(filename, codebase + offset);
    }
    else
    {
        WCHAR assemblyname[MAX_PATH + 8];

        hr = CLASS_E_CLASSNOTAVAILABLE;
        WARN("CodeBase value cannot be found, trying Assembly.\n");
        /* get the last subkey of InprocServer32 */
        res = RegQueryInfoKeyW(key, 0, 0, 0, &numKeys, 0, 0, 0, 0, 0, 0, 0);
        if (res != ERROR_SUCCESS || numKeys == 0)
            goto cleanup;
        numKeys--;
        keyLength = sizeof(subkeyName) / sizeof(WCHAR);
        res = RegEnumKeyExW(key, numKeys, subkeyName, &keyLength, 0, 0, 0, 0);
        if (res != ERROR_SUCCESS)
            goto cleanup;
        res = RegOpenKeyExW(key, subkeyName, 0, KEY_READ, &subkey);
        if (res != ERROR_SUCCESS)
            goto cleanup;
        dwBufLen = MAX_PATH + 8;
        res = RegGetValueW(subkey, NULL, wszAssembly, RRF_RT_REG_SZ, NULL, assemblyname, &dwBufLen);
        RegCloseKey(subkey);
        if (res != ERROR_SUCCESS)
            goto cleanup;

        hr = get_file_from_strongname(assemblyname, filename, MAX_PATH);
        if (!SUCCEEDED(hr))
        {
            /*
             * The registry doesn't have a CodeBase entry and it's not in the GAC.
             *
             * Use the Assembly Key to retrieve the filename.
             *    Assembly : REG_SZ : AssemblyName, Version=X.X.X.X, Culture=neutral, PublicKeyToken=null
             */
            WCHAR *ns;

            WARN("Attempt to load from the application directory.\n");
            GetModuleFileNameW(NULL, filename, MAX_PATH);
            ns = strrchrW(filename, '\\');
            *(ns+1) = '\0';

            ns = strchrW(assemblyname, ',');
            *(ns) = '\0';
            strcatW(filename, assemblyname);
            *(ns) = '.';
            strcatW(filename, wszDLL);
        }
    }

    TRACE("filename (%s)\n", debugstr_w(filename));

    *ppObj = NULL;


    hr = get_runtime_info(filename, NULL, NULL, 0, 0, FALSE, &info);
    if (SUCCEEDED(hr))
    {
        hr = ICLRRuntimeInfo_GetRuntimeHost(info, &host);

        if (SUCCEEDED(hr))
            hr = RuntimeHost_GetDefaultDomain(host, &domain);

        if (SUCCEEDED(hr))
        {
            MonoImage *image;
            MonoClass *klass;
            MonoObject *result;
            IUnknown *unk = NULL;
            char *filenameA, *ns;
            char *classA;

            hr = CLASS_E_CLASSNOTAVAILABLE;

            mono_thread_attach(domain);

            filenameA = WtoA(filename);
            assembly = mono_domain_assembly_open(domain, filenameA);
            HeapFree(GetProcessHeap(), 0, filenameA);
            if (!assembly)
            {
                ERR("Cannot open assembly %s\n", filenameA);
                goto cleanup;
            }

            image = mono_assembly_get_image(assembly);
            if (!image)
            {
                ERR("Couldn't get assembly image\n");
                goto cleanup;
            }

            classA = WtoA(classname);
            ns = strrchr(classA, '.');
            *ns = '\0';

            klass = mono_class_from_name(image, classA, ns+1);
            HeapFree(GetProcessHeap(), 0, classA);
            if (!klass)
            {
                ERR("Couldn't get class from image\n");
                goto cleanup;
            }

            /*
             * Use the default constructor for the .NET class.
             */
            result = mono_object_new(domain, klass);
            mono_runtime_object_init(result);

            hr = RuntimeHost_GetIUnknownForObject(host, result, &unk);
            if (SUCCEEDED(hr))
            {
                hr = IUnknown_QueryInterface(unk, &IID_IUnknown, ppObj);

                IUnknown_Release(unk);
            }
            else
                hr = CLASS_E_CLASSNOTAVAILABLE;
        }
        else
            hr = CLASS_E_CLASSNOTAVAILABLE;
    }
    else
        hr = CLASS_E_CLASSNOTAVAILABLE;

cleanup:
    if(info)
        ICLRRuntimeInfo_Release(info);

    RegCloseKey(key);

    return hr;
}
示例#14
0
文件: xmono.cpp 项目: 0bj3ct/xmono
static void replace_method (Package *pkg) {
    xmono::ReplaceMethodReq req;
    xmono::ReplaceMethodRsp rsp;
    std::string str((char*)pkg->body, pkg->all_len - sizeof (Package));
    if (!req.ParseFromString (str)) {
        LOGD ("xmono::ReplaceMethodReq ParseFromString err!");
        return;
    }
    std::string err;
    void *p, *old_p;
    uint8_t *code;
    int code_size;
    MonoMethodHeader *mh;
    MonoThread *thread;
    MonoMethod *new_method;
    MonoDomain *domain;
    MonoMethod * method = get_method_with_token (req.image_name ().c_str (), req.method_token ());
    if (!method) {
        rsp.set_err (false);
        rsp.set_msg (helper_last_err ());
        goto replace_method_end;
    }
    domain = mono_domain_get_by_id (req.domain_id ());
    if (!domain) {
        rsp.set_err (false);
        rsp.set_msg ("can not get the domain from id");
        goto replace_method_end;
    }
    mh = mono_method_get_header (method);
    if (req.ex_size () != mono_method_header_get_num_clauses (mh)) {
        rsp.set_err (false);
        rsp.set_msg ("ex size != mono_method_header_clauses size!");
        goto replace_method_end;
    }
    for (int i = 0; i < req.ex_size (); i++) {
        xmono::ReplaceMethodReq_ExceptionClause const &e = req.ex (i);
        void *iter = 0;
        MonoExceptionClause *clauses = &mh->clauses[i];
        MonoExceptionClause *old_e = (MonoExceptionClause*)iter;
        old_e->try_offset = e.try_offset ();
        old_e->try_len = e.try_len ();
        old_e->handler_offset = e.handler_offset ();
        old_e->handler_len = e.handler_len ();
    }
    code = new uint8_t[req.new_code ().size ()];
    memcpy (code, req.new_code ().c_str (), req.new_code ().size ());
    mh->code = code;
    mh->code_size = req.new_code ().size ();
    thread = mono_thread_attach (domain);
    /*128 是一个估计值, 在未来可能不稳定, 但当前只能如此*/
    new_method = (MonoMethod*)calloc (128, 1); /*这个地方用malloc优于用new*/
    memcpy (new_method, method, 128);

    pthread_mutex_lock (&replace_mutex);
    replace_method_dict[new_method] = true;
    pthread_mutex_unlock (&replace_mutex);

    p = mono_compile_method (new_method);
    memcpy (hooked_method_dict[method]->specific_hook + 4, &p, 4);

    pthread_mutex_lock (&hooked_mutex);
    old_p = mono_jit_info_get_code_start (hooked_method_dict[method]->jinfo);
    pthread_mutex_unlock (&hooked_mutex);

    mono_thread_detach (thread);
    LOGD ("compile method, new ptr : %p, old ptr : %p", p, old_p);
    rsp.set_err (true);
    rsp.set_msg ("replace_method successful.");
replace_method_end:
    std::string out;
    rsp.SerializeToString (&out);
    ecmd_send (XMONO_ID_REPLACE_METHOD_RSP, (uint8_t const*)out.c_str (), out.size ());
    return;
}
示例#15
0
void CPipeServer::InitMono()
{
	HMODULE hMono=GetModuleHandle(L"mono.dll");

	if (!hMono)
	{
		//this process doesn't use mono.dll  Perhaps it's renamed.  Find a module that exports mono_thread_attach
		HANDLE ths=CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, GetCurrentProcessId());
		if (ths != INVALID_HANDLE_VALUE)
		{
			MODULEENTRY32 me;
			me.dwSize = sizeof(me);
			
			if (Module32First(ths, &me))
			{
				do
				{
					if (GetProcAddress(me.hModule, "mono_thread_attach"))
					{
						hMono = me.hModule;
						break;
					}

				} while (Module32Next(ths, &me));

			}



			CloseHandle(ths);
		}


	}

	WriteQword((UINT64)hMono);
	if (hMono)
	{		
		std::stringstream x;
		x.clear();
		x << "Mono dll found at " << std::hex << hMono <<"\n";
		OutputDebugStringA(x.str().c_str());

		if (attached==FALSE)
		{
			

			g_free=(G_FREE)GetProcAddress(hMono, "g_free");
			mono_get_root_domain=(MONO_GET_ROOT_DOMAIN)GetProcAddress(hMono, "mono_get_root_domain");
			mono_thread_attach=(MONO_THREAD_ATTACH)GetProcAddress(hMono, "mono_thread_attach");
			mono_thread_detach=(MONO_THREAD_DETACH)GetProcAddress(hMono, "mono_thread_detach");

			mono_object_get_class=(MONO_OBJECT_GET_CLASS)GetProcAddress(hMono, "mono_object_get_class");
			
			mono_domain_foreach=(MONO_DOMAIN_FOREACH)GetProcAddress(hMono, "mono_domain_foreach");
			mono_domain_set=(MONO_DOMAIN_SET)GetProcAddress(hMono, "mono_domain_set");
			mono_assembly_foreach=(MONO_ASSEMBLY_FOREACH)GetProcAddress(hMono, "mono_assembly_foreach");
			mono_assembly_get_image=(MONO_ASSEMBLY_GET_IMAGE)GetProcAddress(hMono, "mono_assembly_get_image");
			
			mono_image_get_name=(MONO_IMAGE_GET_NAME)GetProcAddress(hMono, "mono_image_get_name");
			mono_image_get_table_info=(MONO_IMAGE_GET_TABLE_INFO)GetProcAddress(hMono, "mono_image_get_table_info");
			mono_image_rva_map=(MONO_IMAGE_RVA_MAP)GetProcAddress(hMono, "mono_image_rva_map");

			mono_table_info_get_rows=(MONO_TABLE_INFO_GET_ROWS)GetProcAddress(hMono, "mono_table_info_get_rows");
			mono_metadata_decode_row_col=(MONO_METADATA_DECODE_ROW_COL)GetProcAddress(hMono, "mono_metadata_decode_row_col");
			mono_metadata_string_heap=(MONO_METADATA_STRING_HEAP)GetProcAddress(hMono, "mono_metadata_string_heap");

			
			mono_class_get=(MONO_CLASS_GET)GetProcAddress(hMono, "mono_class_get");		
			mono_class_from_name_case=(MONO_CLASS_FROM_NAME_CASE)GetProcAddress(hMono, "mono_class_from_name_case");	
			mono_class_get_name=(MONO_CLASS_GET_NAME)GetProcAddress(hMono, "mono_class_get_name");
			mono_class_get_namespace=(MONO_CLASS_GET_NAMESPACE)GetProcAddress(hMono, "mono_class_get_namespace");
			mono_class_get_methods=(MONO_CLASS_GET_METHODS)GetProcAddress(hMono, "mono_class_get_methods");		
			mono_class_get_method_from_name=(MONO_CLASS_GET_METHOD_FROM_NAME)GetProcAddress(hMono, "mono_class_get_method_from_name");		
			mono_class_get_fields=(MONO_CLASS_GET_FIELDS)GetProcAddress(hMono, "mono_class_get_fields");	
			mono_class_get_parent=(MONO_CLASS_GET_PARENT)GetProcAddress(hMono, "mono_class_get_parent");
			mono_class_vtable=(MONO_CLASS_VTABLE)GetProcAddress(hMono, "mono_class_vtable");
			
			mono_class_num_fields=(MONO_CLASS_NUM_FIELDS)GetProcAddress(hMono, "mono_class_num_fields");	
			mono_class_num_methods=(MONO_CLASS_NUM_METHODS)GetProcAddress(hMono, "mono_class_num_methods");		
			

			mono_field_get_name=(MONO_FIELD_GET_NAME)GetProcAddress(hMono, "mono_field_get_name");	
			mono_field_get_type=(MONO_FIELD_GET_TYPE)GetProcAddress(hMono, "mono_field_get_type");	
			mono_field_get_parent=(MONO_FIELD_GET_PARENT)GetProcAddress(hMono, "mono_field_get_parent");	
			mono_field_get_offset=(MONO_FIELD_GET_OFFSET)GetProcAddress(hMono, "mono_field_get_offset");	
			mono_field_get_flags = (MONO_FIELD_GET_FLAGS)GetProcAddress(hMono, "mono_field_get_flags");

			mono_type_get_name=(MONO_TYPE_GET_NAME)GetProcAddress(hMono, "mono_type_get_name");
			mono_type_get_type=(MONO_TYPE_GET_TYPE)GetProcAddress(hMono, "mono_type_get_type");

			mono_method_get_name=(MONO_METHOD_GET_NAME)GetProcAddress(hMono, "mono_method_get_name");	
			mono_method_get_class=(MONO_METHOD_GET_CLASS)GetProcAddress(hMono, "mono_method_get_class");	
			mono_method_get_header=(MONO_METHOD_GET_HEADER)GetProcAddress(hMono, "mono_method_get_header");	
			mono_method_signature=(MONO_METHOD_SIG)GetProcAddress(hMono, "mono_method_signature");
			mono_method_get_param_names = (MONO_METHOD_GET_PARAM_NAMES)GetProcAddress(hMono, "mono_method_get_param_names");

			

			mono_signature_get_desc = (MONO_SIGNATURE_GET_DESC)GetProcAddress(hMono, "mono_signature_get_desc");
			mono_signature_get_param_count = (MONO_SIGNATURE_GET_PARAM_COUNT)GetProcAddress(hMono, "mono_signature_get_param_count");
			mono_signature_get_return_type = (MONO_SIGNATURE_GET_RETURN_TYPE)GetProcAddress(hMono, "mono_signature_get_return_type");
			


			mono_compile_method=(MONO_COMPILE_METHOD)GetProcAddress(hMono, "mono_compile_method");	
			mono_free_method=(MONO_FREE_METHOD)GetProcAddress(hMono, "mono_free_method");	
			mono_jit_info_table_find=(MONO_JIT_INFO_TABLE_FIND)GetProcAddress(hMono, "mono_jit_info_table_find");	
			mono_jit_info_get_method=(MONO_JIT_INFO_GET_METHOD)GetProcAddress(hMono, "mono_jit_info_get_method");	
			mono_jit_info_get_code_start=(MONO_JIT_INFO_GET_CODE_START)GetProcAddress(hMono, "mono_jit_info_get_code_start");	
			mono_jit_info_get_code_size=(MONO_JIT_INFO_GET_CODE_SIZE)GetProcAddress(hMono, "mono_jit_info_get_code_size");	

			mono_method_header_get_code=(MONO_METHOD_HEADER_GET_CODE)GetProcAddress(hMono, "mono_method_header_get_code");	
			mono_disasm_code=(MONO_DISASM_CODE)GetProcAddress(hMono, "mono_disasm_code");	

			mono_vtable_get_static_field_data = (MONO_VTABLE_GET_STATIC_FIELD_DATA)GetProcAddress(hMono, "mono_vtable_get_static_field_data");

			
			if (mono_get_root_domain==NULL) OutputDebugStringA("mono_get_root_domain not assigned");
			if (mono_thread_attach==NULL) OutputDebugStringA("mono_thread_attach not assigned");
			if (mono_object_get_class==NULL) OutputDebugStringA("mono_object_get_class not assigned");
			if (mono_class_get_name==NULL) OutputDebugStringA("mono_class_get_name not assigned");
			if (mono_domain_foreach==NULL) OutputDebugStringA("mono_domain_foreach not assigned");
			if (mono_domain_set==NULL) OutputDebugStringA("mono_domain_set not assigned");
			if (mono_assembly_foreach==NULL) OutputDebugStringA("mono_assembly_foreach not assigned");
			if (mono_assembly_get_image==NULL) OutputDebugStringA("mono_assembly_get_image not assigned");
			if (mono_image_get_name==NULL) OutputDebugStringA("mono_image_get_name not assigned");


			mono_selfthread=mono_thread_attach(mono_get_root_domain());
			attached=TRUE;
		}
		else
			OutputDebugStringA("Already attached");
	}
}