<commit_before>// Copyright 2006 <NAME> <<EMAIL>>
// This software is made available under the MIT License
// See COPYING for details

using System;
using System.IO;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.Remoting.Proxies;
using System.Runtime.Remoting.Messaging;

namespace NDesk.DBus
{
	public class DProxy : RealProxy
	{
		Connection conn;

		string bus_name;
		ObjectPath object_path;

		//Dictionary<string,string> methods = new Dictionary<string,string> ();

		public DProxy (Connection conn, string bus_name, ObjectPath object_path, Type type) : base(type)
		{
			this.conn = conn;
			this.bus_name = bus_name;
			this.object_path = object_path;

			//messy and only relevant to imported objects, but works
			//note that the foreach is useless since there can be only key
			//probably does not deal with class inheritance etc.

			foreach (InterfaceAttribute ia in type.GetCustomAttributes (typeof (InterfaceAttribute), false))
				conn.RegisteredTypes[type] = ia.Name;

			foreach (Type t in type.GetInterfaces ())
				foreach (InterfaceAttribute ia in t.GetCustomAttributes (typeof (InterfaceAttribute), false))
					conn.RegisteredTypes[t] = ia.Name;

			/*
			methods["Hello"] = "";
			methods["ListNames"] = "";
			methods["NameHasOwner"] = "s";
			*/
		}

		public override IMessage Invoke (IMessage msg)
		{
			IMethodCallMessage mcm = (IMethodCallMessage) msg;

			MethodReturnMessageWrapper newRet = new MethodReturnMessageWrapper ((IMethodReturnMessage) msg);

			//Console.WriteLine (mcm.MethodName);

			//if (!methods.ContainsKey (mcm.MethodName))
			//	return null;

			//foreach (object myObj in mcm.InArgs)
			//	Console.WriteLine("arg value: " + myObj.ToString());

			if (mcm.MethodName.StartsWith ("add_")) {
				string[] parts = mcm.MethodName.Split ('_');
				string ename = parts[1];
				Delegate dlg = (Delegate)mcm.InArgs[0];

				conn.Handlers[ename] = dlg;

				//TODO: make the match rule more specific, and cache the DBus object somewhere sensible
				if (bus_name != "org.freedesktop.DBus") {
					org.freedesktop.DBus.Bus bus = conn.GetInstance<org.freedesktop.DBus.Bus> ("org.freedesktop.DBus", new ObjectPath ("/org/freedesktop/DBus"));
					bus.AddMatch ("type='signal',sender='" + bus_name + "',member='" + ename + "'");
				}

				return (IMethodReturnMessage) newRet;
			}

			if (mcm.MethodName.StartsWith ("remove_")) {
				string[] parts = mcm.MethodName.Split ('_');
				string ename = parts[1];
				//Delegate dlg = (Delegate)mcm.InArgs[0];

				//TODO: make the match rule more specific, and cache the DBus object somewhere sensible
				if (bus_name != "org.freedesktop.DBus") {
					org.freedesktop.DBus.Bus bus = conn.GetInstance<org.freedesktop.DBus.Bus> ("org.freedesktop.DBus", new ObjectPath ("/org/freedesktop/DBus"));
					bus.RemoveMatch ("type='signal',sender='" + bus_name + "',member='" + ename + "'");
				}

				conn.Handlers.Remove (ename);

				return (IMethodReturnMessage) newRet;
			}

			Message callMsg = new Message ();

			//build the outbound method call message
			{

				Signature inSig = new Signature ("");

				if (mcm.InArgs != null && mcm.InArgs.Length != 0) {
					callMsg.Body = new System.IO.MemoryStream ();

					foreach (object arg in mcm.InArgs)
						Message.Write (callMsg.Body, arg.GetType (), arg);

					inSig = GetSig (mcm.InArgs);
				}

				string iface = null;

				//if the type is registered, use that, otherwise use legacy iface string
				MethodInfo imi = mcm.MethodBase as MethodInfo;
				if (imi != null && conn.RegisteredTypes.ContainsKey (imi.DeclaringType))
					iface = conn.RegisteredTypes[imi.DeclaringType];

				if (inSig.Data.Length == 0)
					callMsg.WriteHeader (new HeaderField (FieldCode.Path, object_path), new HeaderField (FieldCode.Interface, iface), new HeaderField (FieldCode.Member, mcm.MethodName), new HeaderField (FieldCode.Destination, bus_name));
				else
					callMsg.WriteHeader (new HeaderField (FieldCode.Path, object_path), new HeaderField (FieldCode.Interface, iface), new HeaderField (FieldCode.Member, mcm.MethodName), new HeaderField (FieldCode.Destination, bus_name), new HeaderField (FieldCode.Signature, inSig));
			}

			bool needsReply = true;

			MethodInfo mi = newRet.MethodBase as MethodInfo;
			if (mi.ReturnType == typeof (void))
				needsReply = false;

			if (!needsReply) {
				conn.Send (callMsg);
				return (IMethodReturnMessage) newRet;
			}

			Message retMsg = conn.SendWithReplyAndBlock (callMsg);

			//handle the reply message
			{
				Type[] retTypeArr = new Type[1];
				retTypeArr[0] = mi.ReturnType;
				newRet.ReturnValue = conn.GetDynamicValues (retMsg, retTypeArr)[0];
			}

			return (IMethodReturnMessage) newRet;
		}

		/*
		public override ObjRef CreateObjRef (Type ServerType)
		{
			throw new System.NotSupportedException ();<commit_msg>Add CLR property to CamelCase mapping<commit_after>// Copyright 2006 <NAME> <<EMAIL>>
// This software is made available under the MIT License
// See COPYING for details

using System;
using System.IO;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.Remoting.Proxies;
using System.Runtime.Remoting.Messaging;

namespace NDesk.DBus
{
	public class DProxy : RealProxy
	{
		Connection conn;

		string bus_name;
		ObjectPath object_path;

		//Dictionary<string,string> methods = new Dictionary<string,string> ();

		public DProxy (Connection conn, string bus_name, ObjectPath object_path, Type type) : base(type)
		{
			this.conn = conn;
			this.bus_name = bus_name;
			this.object_path = object_path;

			//messy and only relevant to imported objects, but works
			//note that the foreach is useless since there can be only key
			//probably does not deal with class inheritance etc.

			foreach (InterfaceAttribute ia in type.GetCustomAttributes (typeof (InterfaceAttribute), false))
				conn.RegisteredTypes[type] = ia.Name;

			foreach (Type t in type.GetInterfaces ())
				foreach (InterfaceAttribute ia in t.GetCustomAttributes (typeof (InterfaceAttribute), false))
					conn.RegisteredTypes[t] = ia.Name;

			/*
			methods["Hello"] = "";
			methods["ListNames"] = "";
			methods["NameHasOwner"] = "s";
			*/
		}

		public override IMessage Invoke (IMessage msg)
		{
			IMethodCallMessage mcm = (IMethodCallMessage) msg;

			MethodReturnMessageWrapper newRet = new MethodReturnMessageWrapper ((IMethodReturnMessage) msg);

			//Console.WriteLine (mcm.MethodName);

			//if (!methods.ContainsKey (mcm.MethodName))
			//	return null;

			//foreach (object myObj in mcm.InArgs)
			//	Console.WriteLine("arg value: " + myObj.ToString());

			if (mcm.MethodName.StartsWith ("add_")) {
				string[] parts = mcm.MethodName.Split ('_');
				string ename = parts[1];
				Delegate dlg = (Delegate)mcm.InArgs[0];

				conn.Handlers[ename] = dlg;

				//TODO: make the match rule more specific, and cache the DBus object somewhere sensible
				if (bus_name != "org.freedesktop.DBus") {
					org.freedesktop.DBus.Bus bus = conn.GetInstance<org.freedesktop.DBus.Bus> ("org.freedesktop.DBus", new ObjectPath ("/org/freedesktop/DBus"));
					bus.AddMatch ("type='signal',sender='" + bus_name + "',member='" + ename + "'");
				}

				return (IMethodReturnMessage) newRet;
			}

			if (mcm.MethodName.StartsWith ("remove_")) {
				string[] parts = mcm.MethodName.Split ('_');
				string ename = parts[1];
				//Delegate dlg = (Delegate)mcm.InArgs[0];

				//TODO: make the match rule more specific, and cache the DBus object somewhere sensible
				if (bus_name != "org.freedesktop.DBus") {
					org.freedesktop.DBus.Bus bus = conn.GetInstance<org.freedesktop.DBus.Bus> ("org.freedesktop.DBus", new ObjectPath ("/org/freedesktop/DBus"));
					bus.RemoveMatch ("type='signal',sender='" + bus_name + "',member='" + ename + "'");
				}

				conn.Handlers.Remove (ename);

				return (IMethodReturnMessage) newRet;
			}

			string methodName = mcm.MethodName;

			//map property accessors
			methodName = methodName.Replace ("get_", "Get");
			methodName = methodName.Replace ("set_", "Set");

			Message callMsg = new Message ();

			//build the outbound method call message
			{

				Signature inSig = new Signature ("");

				if (mcm.InArgs != null && mcm.InArgs.Length != 0) {
					callMsg.Body = new System.IO.MemoryStream ();

					foreach (object arg in mcm.InArgs)
						Message.Write (callMsg.Body, arg.GetType (), arg);

					inSig = GetSig (mcm.InArgs);
				}

				string iface = null;

				//if the type is registered, use that, otherwise use legacy iface string
				MethodInfo imi = mcm.MethodBase as MethodInfo;
				if (imi != null && conn.RegisteredTypes.ContainsKey (imi.DeclaringType))
					iface = conn.RegisteredTypes[imi.DeclaringType];

				if (inSig.Data.Length == 0)
					callMsg.WriteHeader (new HeaderField (FieldCode.Path, object_path), new HeaderField (FieldCode.Interface, iface), new HeaderField (FieldCode.Member, methodName), new HeaderField (FieldCode.Destination, bus_name));
				else
					callMsg.WriteHeader (new HeaderField (FieldCode.Path, object_path), new HeaderField (FieldCode.Interface, iface), new HeaderField (FieldCode.Member, methodName), new HeaderField (FieldCode.Destination, bus_name), new HeaderField (FieldCode.Signature, inSig));
			}

			bool needsReply = true;

			MethodInfo mi = newRet.MethodBase as MethodInfo;
			if (mi.ReturnType == typeof (void))
				needsReply = false;

			if (!needsReply) {
				conn.Send (callMsg);
				return (IMethodReturnMessage) newRet;
			}

			Message retMsg = conn.SendWithReplyAndBlock (callMsg);

			//handle the reply message
			{
				Type[] retTypeArr = new Type[1];
				retTypeArr[0] = mi.ReturnType;
				newRet.ReturnValue = conn.GetDynamicValues (retMsg, retTypeArr)[0];
			}

			return (IMethodReturnMessage) newRet;
		}

		/*
		public override ObjRef CreateObjRef (Type ServerType)
		{
			throw new System.NotSupportedException ();
{'fraction_non_alphanumeric': 0.12384996461429583, 'fraction_numerical': 0.0026286523101809725, 'mean_word_length': 3.746641074856046, 'pattern_counts': {'":': 0, '<': 17, '<?xml version=': 0, '>': 17, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '690712', 'n_tokens_mistral': 3634, 'n_tokens_neox': 3035, 'n_words': 815}