Posts tagged ‘.Net’

Reflection with Private Members

By using reflection we can call any function including the private and protected ones. This includes private static methods, constructor methods, normal methods. What we need to do is to get the method by the BindingFlags.Nonpublic flag and then we just use it like a reflected type.

using System;
using System.Collections.Generic;
using System.Text;
using System.Reflection;
 
namespace ReflectPrivateMembers
{
    class Program
    {
        static void Main(string[] args)
        {
            ConstructorInfo ci = typeof(Hello).GetConstructor(BindingFlags.NonPublic| BindingFlags.Instance ,null,System.Type.EmptyTypes,null);
            object helloObject = ci.Invoke(System.Type.EmptyTypes);
            MethodInfo[] helloObjectMethods = helloObject.GetType().GetMethods(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.DeclaredOnly| BindingFlags.Instance );
 
            foreach (MethodInfo mi in helloObjectMethods)
            {
                mi.Invoke(helloObject, System.Type.EmptyTypes);
            }
            Console.ReadLine();
        }
    }
    public class Hello
    {
        private Hello()
        {
            Console.WriteLine("Private Constructor");
        }
        public void HelloPub()
        {
            Console.WriteLine("Public Hello");
        }
        private void HelloPriv()
        {
            Console.WriteLine("Private Hello");
        }
    }
}

XML Class Generator for C# using XSD for deserialization

Let’s say we have an XML file and we want to deserialize that file to our implemented class. This is an easy task if the XML file is simple. However if it has more complex types, it can take a long time to implement the class without error. XSD comes with .Net framework SDK. I does not have a user interface, we can access it from the command line tools.

  1. We start it from Visual Studio 2005 -> Visual Studio Tools -> Visual Studio Command Prompt .
  2. Next we need to have a valid XML file that I want to generate the class from. I just use for this sample, the xml output of the yahoo search REST query. Just dowload the xml output of the query
    Yahoo Search xml+class+generator or any other xml file that you want to generate the class from. We save the file as xml.
  3. We use the command xsd to the xml file to generate the xsd schema file.
  4. D:\\test>xsd webSearch.xml
    Microsoft (R) Xml Schemas/DataTypes support utility
    [Microsoft (R) .NET Framework, Version 2.0.50727.42]
    Copyright (C) Microsoft Corporation. All rights reserved.
    Writing file ‘D:\\test\\webSearch.xsd’.
    D:\\test>

  5. Next we use the generated xsd file to generate our class. The generated xsd can contain multiple class, so it would be better to use /classes switch. The default language is C#; however you might want to use it in your Visual Basic Project, to do that just add the switch /language:vb
  6. D:\\test>xsd webSearch.xsd /CLASSES /language:vb
    Microsoft (R) Xml Schemas/DataTypes support utility
    [Microsoft (R) .NET Framework, Version 2.0.50727.42]
    Copyright (C) Microsoft Corporation. All rights reserved.
    Writing file ‘D:\\test\\webSearch.vb’.
    D:\\test>xsd webSearch.xsd /CLASSES
    Microsoft (R) Xml Schemas/DataTypes support utility
    [Microsoft (R) .NET Framework, Version 2.0.50727.42]
    Copyright (C) Microsoft Corporation. All rights reserved.
    Writing file ‘D:\\test\\webSearch.cs’.

  7. Now we have the class file that we use to deserialize the xml object without any exception. So I add the XML file and the generated cs file to my project.
  8. using System;
    using System.Collections.Generic;
    using System.Text;
     
    namespace XSDTest
    {
        class Program
        {
            static void Main(string[] args)
            {
                System.IO.StreamReader str = new System.IO.StreamReader("webSearch.xml");
                System.Xml.Serialization.XmlSerializer xSerializer = new System.Xml.Serialization.XmlSerializer(typeof(ResultSet));
                ResultSet res = (ResultSet) xSerializer.Deserialize(str);
                foreach (ResultSetResult r in res.Result)
                {
                    Console.WriteLine(r.Title);
                    Console.WriteLine(r.Summary);
                    Console.WriteLine();
                }
                str.Close();
     
                Console.ReadLine();
            }
        }
    }

  9. Here is the output :
  10. XML Class Generator for C++
    Oracle9i XML Developer’s Kits Guide – XDK. Release 2 (9.2) Part Number A96621-01
    . 19. XML Class Generator for C++ This chapter contains the following sections:
    Accessing XML C++ Class Generator … Accessing XML C++ Class Generator. The XML
    C++ Class Generator is provided with Oracle9i and is also available for XML Class Generator for Java
    Oracle9i XML Developer’s Kits Guide – XDK. Release 2 (9.2) Part Number A96621-01
    . 7. XML Class Generator for Java. This chapter contains the following sections:
    Accessing XML Class Generator for Java … The Oracle XML Class Generator for Java is provided with Oracle9i’s XDK for Java …

As you may see this is the easiest and exceptionless solution for using xml output of some web services. What we simply do is generate the classfile, deserialize the xml file to our class and use it.

Download

.

The coolest exception I’ve ever get : FatalExecutionError

I get the coolest exception from .Net FatalExecutionError. What is cool for that exception is that it is assuming that itself might be wrong. “This error may be a bug in the CLR.” So I might not be the one who generated, I can just blame CLR for doing that :)

FatalExecutionError

“The runtime has encountered a fatal error. The address of the error was at
0x79eebbc1, on thread 0x141c. The error code is 0xc0000005. This error may
be a bug in the CLR or in the unsafe or non-verifiable portions of user
code. Common sources of this bug include user marshaling errors for
COM-interop or PInvoke, which may corrupt the stack.”

Luckily this is not a bug in the CLR. It was my fault. In this sample project, I try to generate a reflected dynamic IL function (I call it like that) to lower the execution time for the reflection. The sample works perfect with value types and reference types, however I have a problem with generic value types. Some boxing and unboxing operation might be faulty in this snippet. What is really causing that error is because I generate IL code dynamically and IL code is the compiled code, the runtime executes the statements of IL, and it gets an internal exception. Normally such a code wouldn’t compile that way so it will continue to operate normally. As a result it suspects from itself.

I will share more on dynamic execution in a later post when I get finished the code and solved my bug.

public class DynamicReflectionHelper
{
    public delegate object GetPropertyFieldDelegate(object obj);
    public static GetPropertyFieldDelegate GetP(object o,string memberName)
    {
        Type v = o.GetType();
        PropertyInfo pi = v.GetProperty(memberName);
        FieldInfo fi = v.GetField(memberName);
 
        if (pi != null || fi != null)
        {   
            DynamicMethod dm = new DynamicMethod( "GetPropertyorField_" + memberName, typeof(object), new Type[] { typeof(object) }, v.Module);
            ILGenerator il = dm.GetILGenerator();
            il.Emit(OpCodes.Ldarg_0);
 
            if (pi.PropertyType.IsValueType)
                il.Emit(OpCodes.Box, pi.PropertyType);
            if (pi.PropertyType.IsGenericType)
                il.Emit(OpCodes.Nop);
 
            if (pi != null)
                il.EmitCall(OpCodes.Callvirt,  pi.GetGetMethod(), null);
            else if (fi != null)
                il.Emit(OpCodes.Ldfld, fi);
 
            il.Emit(OpCodes.Ret);
            return (GetPropertyFieldDelegate) dm.CreateDelegate( typeof(GetPropertyFieldDelegate));
        }
        else
            throw new NullReferenceException("No property or Field");
    }
}

Value Types vs Reference Types – Boxing Unboxing

In a custom control, I wrote a general function to handle the object equality. I have used it several times without error. However today I sent a value type instead of a reference type, and some unexpected results occured.

The base class object have some basic methods which other classes override those methods. One of the methods is Equals. Although equals usually compares references of objects,many .Net framework internal classes implement that method like in System.String class it can compare the contents. When we go back to object and call equals method the object polymorphism occurs . This is not true for value types. When we box the value type as a reference type, it creates a new memory space for that. So for each boxing a separate memory block allocated, and the reference comparison normally returns false. Here is the sample how it behaves.

using System;
 
public class MyClass
{
	public static void Main()
	{
		string s1 = "can";
		string s2 = "can";
		Console.WriteLine("s1== s2  {0}",s1==s2 ); 
 
		object oo1 = new object();
		object oo2 = new object();
		Console.WriteLine("oo1== oo2  {0}",oo1==oo2 ); 
 
		decimal d1 = 5;
		decimal d2 = 5;
		Console.WriteLine("d1== d2  {0}",d1==d2 ); 
 
		object o1 = d1;
		object o2 = d2;
		Console.WriteLine("o1== o2 {0}", o1==o2);
 
		Console.ReadLine();
	}
}

Below is the output

s1== s2  True
oo1== oo2  False
d1== d2  True
o1== o2  False
_

Messenger Add-in -> MSN Messenger API

I was surfing on the developer site of Windows Live . I saw the new (for me) MSN SDK. Lastly there was only activity sdk which is not real SDK.
The new Messenger Add-in SDK is included inside MSN Live messenger, althought the site says it is a seperate download.

Anyway to use it,

  • Add the key to windows registry -> HKEY_CURRENT_USER\ Software\ Microsoft\ MSNMessenger\ AddInFeatureEnabled 1
  • Registry Settings

  • Create a class library project
  • Add MessengerClient.dll which is located on the messenger installation directory
  • Use the interface to create the addin, the code will guide you on how to do that
  • public class AutoReply : IMessengerAddIn
        {
            MessengerClient m_messenger;
     
            void IMessengerAddIn.Initialize(MessengerClient messenger)
            {
                m_messenger = messenger;
                AddInProperties properties = m_messenger.AddInProperties;
                properties.Creator = "Can Erten";
                properties.Description = "Test";
     
                m_messenger.IncomingTextMessage += new EventHandler<IncomingTextMessageEventArgs>
    (m_messenger_IncomingTextMessage);
            }
     
            void m_messenger_IncomingTextMessage(object sender, IncomingTextMessageEventArgs e)
            {
                m_messenger.SendTextMessage("Unavailable..." + e.UserFrom.FriendlyName, e.UserFrom);
                if (m_messenger.LocalUser.Status != UserStatus.Online)
                {
                    string message = m_messenger.LocalUser.PersonalStatusMessage;
                    m_messenger.SendTextMessage("Unavailable..." + e.UserFrom.FriendlyName, e.UserFrom);
                }
            }
     
        }


    As you can see it is very simple and well developed class library. Thanks to MSN team for being that clear.

  • The different part for the delivery is the assembly name. You need to change the assembly name to the namespace and class name.
  • Run Msn messenger, in the options windows, addin tab add your dll file. That’s it.
  • MSN Window

Finally you might want to debug the addin. To do this in visual studio, attach to msn process, make breakpoints and here we go, just debug as normally you do :)
attach

Windows Communication Foundation – Simple Web Service Call

Invoking web services is not much different in windows communication foundation. We have a tool svcutil that generates the interface and the proxy class automatically, I think this will be included later on the IDE. For this sample call I just used google search service. We use the command svcutil with the wsdl adress of the web service, and the program generates a config file and a class file for the service to use.

C:\\Program Files\\Microsoft Visual Studio 8\\VC>svcutil d:\\api\\googleapi\\googlesea
rch.wsdl
Microsoft (R) Service Model Metadata Tool
[Microsoft? .NET Framework, Version 3.0.3906.22]
Copyright (c) Microsoft Corporation.  All rights reserved.

Generating files...
C:\\Program Files\\Microsoft Visual Studio 8\\VC\\GoogleSearch.cs
C:\\Program Files\\Microsoft Visual Studio 8\\VC\\output.config

There is also a graphical utility for doing that operation called “Service Configuration Editor”, however as far as I can see this tool only takes the output of the config file. It provides easy to use property controls for modifying the file but the command line versions generated file has some more details on it.

Service Configuration Editor

Below is the snippets from the generated file.

The config file specifies the services ABCs ->

  • Adress
  • Binding
  • Contract
		<client>
			<endpoint address="http://api.google.com/search/beta2" binding="basicHttpBinding"
                bindingConfiguration="GoogleSearchBinding" contract="GoogleSearchPort"
                name="GoogleSearchPort" />
		</client>

ServiceContract setting in the config file specifies the interface implemented the ServiceContractAttribute class. Here is the GoogleSearchPort interface is the serviceContract.

[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")]
[System.ServiceModel.ServiceContractAttribute(Namespace = "urn:GoogleSearch")]
public interface GoogleSearchPort
{
    [System.ServiceModel.OperationContractAttribute(Action = "urn:GoogleSearchAction", ReplyAction = "*")]
    [System.ServiceModel.XmlSerializerFormatAttribute(Style = System.ServiceModel.OperationFormatStyle.Rpc, Use = System.ServiceModel.OperationFormatUse.Encoded)]
    [System.ServiceModel.ServiceKnownTypeAttribute(typeof(ResultElement))]
    [return: System.ServiceModel.MessageParameterAttribute(Name = "return")]
    GoogleSearchResult doGoogleSearch(string key, string q, int start, int maxResults, bool filter, string restrict, bool safeSearch, string lr, string ie, string oe);

I just created a new console application project and added these files to the project. Also added the reference “System.ServiceModel” for wcf to work. The rest is the same as previously calling web services, the generated proxy class includes all the information to get the data from the config file. So only thing I have to do is to instanciate and use it.

 class Program
    {
        static void Main(string[] args)
        {
            using (GoogleSearchPortProxy proxy = new GoogleSearchPortProxy())
            {
 
                string key = "secretCode";
                string query = "wcf";
                GoogleSearchResult res = proxy.doGoogleSearch(key, query, 0, 10, false, "", false, "", "", "");
 
                foreach (ResultElement r in res.resultElements)
                {
                    Console.ForegroundColor = ConsoleColor.Blue;
                    Console.WriteLine(r.title);
 
                    Console.ForegroundColor = ConsoleColor.Gray;
                    Console.WriteLine(r.URL);
 
                    Console.ForegroundColor = ConsoleColor.White;
                    Console.WriteLine(r.snippet);
                }
                Console.ReadLine();
            }
        }
    }

Here is the output of the web service results.

Windows Communication Foundation

http://msdn.microsoft.com/webservices/indigo/default.aspx

Explore "Indigo," a set of .NET technologies for building and managing
 service-oriented  systems.
Get Connected

http://msdn.microsoft.com/windowsvista/prodinfo/what/connected/default.aspx

The Windows Communication Foundation Web service APIs make it easy to bui
ld and  consume secure, reliable, and transacted Web services.
Welcome to WCF

http://www.wcf.co.uk/