.NET Interoperability at a Glance 2 – Managed Code Interoperation

No.of Views543
Bookmarked0 times
Downloads 
Votes0
By  Geming Leader   On  28 Dec 2010 10:12:58
Tag : CSharp , PInvoke
In the previous article, you learn what interoperability is and how it relates to the .NET Framework. In this article, we’re going to talk about the first form of interoperability, the Managed Code Interop. In the next article, we’ll talk about the other forms.
emailbookmarkadd commentsprint

Images in this article missing? We recently lost them in a site migration. We're working to restore these as you read this. Should you need an image in an emergency, please contact us at info@codegain.com

 

This article is available in my blog too, check it out here.

See more Interoperability examples here.

Contents

Contents of this article:

  • Contents
  • Read also
  • Overview
  • Introduction
  • Forms of Interop
  • Managed Code Interop
  • Summary
  • Where to go next

Read also

More from this series:

Overview

In the previous article, you learnt what interoperability is and how it relates to the .NET Framework. In this article, we’re going to talk about the first form of interoperability, the Managed Code Interop. In the next article, we’ll talk about the other forms.

Introduction

So, to understand Interoperation well in the .NET Framework, you must see it in action. In this article, we’ll talk about the first form of .NET interoperability and see how to implement it using the available tools.

Just a reminder, Interoperability is the process of communication between two separate systems. In .NET Interop, the first system is always the .NET Framework; the other system might be any other technology.

Forms of Interop

Interoperability in .NET Framework has two forms:

  • Managed Code Interoperability
  • Unmanaged Code Interoperability

Next, we have a short discussion of each of the forms.

Managed Code Interop

This was one of the main goals of .NET Framework. Managed Code Interoperability means that you can easily communicate with any other .NET assembly no matter what language used to build that assembly.

Not surprisingly, because of the nature of .NET Framework and its runtime engine (the CLR,) .NET code supposed to be called Managed Code, while any other code is  unmanaged.

To see this in action, let’s try this:

  1. Create a new Console application in the language you like (C#/VB.NET.)
  2. Add a new Class Library project to the solution and choose another language other than the one used in the first project.
  3. In the Class Library project, add the following code (choose the suitable project):
    // C#
    
    public static class Hello
    {
        public static string SayHello(string name)
        {
            return "Hello, " + name;
        }
    }
    ' VB.NET
    
    Public Module Hello
        Public Function SayHello(ByVal name As String) As String
            Return "Hello, " & name
        End Function
    End Module
  4. Now, go back to the Console application. Our goal is to call the function we have added to the other project. To do this, you must first add a reference to the library in the first project. Right-click the Console project in Solution Explorer and choose Add Reference to open the Add Reference dialog (figure 1.) Go to the Projects tab and select the class library project to add it.
    Image Loading

    Figure 1 - Add Reference to a friend project

  5. Now you can add the following code to the Console application to call the SayHello() function of the class library.
    // C#
    
    static void Main()
    {
        Console.WriteLine(ClassLibrary1.Hello.SayHello("Mohammad Elsheimy"));
    }
    ' VB.NET
    
    Sub Main()
        Console.WriteLine(ClassLibrary1.Hello.SayHello("Mohammad Elsheimy"))
    End Sub

How this happened? How could we use the VB.NET module in C# which is not available there (or the C#’s static class in VB which is not available there too)?

Not just that, but you can inherit C# classes from VB.NET (and vice versa) and do all you like as if both were created using the same language. The secret behind this is the Common Intermediate Language (CIL.)

When you compile your project, the compiler actually doesn’t convert your C#/VB.NET code to instructions in the Machine language. Rather, it converts your code to another language of the .NET Framework, which is the Common Intermediate Language. The Common Intermediate Language, or simply CIL, is the main language of .NET Framework which inherits all the functionalities of the framework, and which all other .NET languages when compiled are converted to it.

So, the CIL fits as a middle layer between your .NET language and the machine language. When you compile your project, the compiler converts your code to CIL statements and emits them in assembly file. In runtime, the compiler reads the CIL from the assembly and converts them to machine-readable statements.

How CIL helps in interoperation? The communication between .NET assemblies is now done through the CIL of the assemblies. Therefore, you don’t need to be aware of structures and statements that are not available in your language since every statement for any .NET language has a counterpart in IL. For example, both the C# static class and VB.NET module convert to CIL static abstract class (see figure 2.)

Image Loading

Figure 2 - CIL and other .NET languages

Managed Interop is not restricted to C# and VB.NET only; it’s about all languages run inside the CLR (i.e. based on .NET Framework.)

If we have a sneak look at the CIL generated from the Hello class which is nearly the same from both VB.NET and C#, we would see the following code:

 

.class public abstract auto ansi sealed beforefieldinit ClassLibrary1.Hello
       extends [mscorlib]System.Object
{

    .method public hidebysig static string  SayHello(string name) cil managed
    {
      // Code size       12 (0xc)
      .maxstack  8
      IL_0000:  ldstr      "Hello, "
      IL_0005:  ldarg.0
      IL_0006:  call       string [mscorlib]System.String::Concat(string,
                                                              string)
      IL_000b:  ret
    } // end of method Hello::SayHello

} // end of class ClassLibrary1.Hello

On the other hand, this is the code generated from the Main function (which is also the same from VB.NET/C#):

 

.class public abstract auto ansi sealed beforefieldinit ConsoleApplication1.Program
       extends [mscorlib]System.Object
{

    .method private hidebysig static void  Main() cil managed
    {
      .entrypoint
      .maxstack  8
      IL_0000:  ldstr      "Mohammad Elsheimy"
      IL_0005:  call       string [ClassLibrary1]ClassLibrary1.Hello::SayHello(string)
      IL_000a:  call       void [mscorlib]System.Console::WriteLine(string)
      IL_000f:  ret
    } // end of method Program::Main

} // end of class ConsoleApplication1.Program

You can use the ILDasm.exe tool to get the CIL code of an assembly. This tool is located in Program Files\Microsoft SDKs\Windows\<version>\bin.

Here comes a question, is there CIL developers? Could we write the CIL directly and build it into .NET assembly? Why we can’t find much (if not any) CIL developers? You can extract the answer from the CIL code itself. As you see, CIL is not so friendly and its statements are not so clear. Plus, if we could use common languages to generate the CIL, we we’d like to program in CIL directly? So it’s better to leave the CIL for the compiler.

Now, let’s see the other form of .NET interoperation, Unmanaged Code Interoperability.

Summary

So, the secret of Managed Code Interoperation falls in the Common Intermediate Language or CIL. When you compile your code, the compiler converts your C#/VB.NET (or any other .NET language) to CIL instructions and saves them in the assembly, and that’s the secret. The linking between .NET assemblies of different languages relies on the fact that the linking is actually done between CILs of the assemblies. The assembly code doesn’t (usually) have any clue about the language used to develop it. In the runtime, the compiler reads those instructions and converts them to machine instructions and execute them.

Next, we’ll talk about the other form of .NET Interoperation, it’s the interoperation with unmanaged code.

Where to go next

Read more about Interoperability here.

More from this series:

 
Sign Up to vote for this article
 
About Author
 
Geming Leader
Occupation-Software Engineer
Company-Just Like a Magic
Member Type-Expert
Location-Egypt
Joined date-30 Jul 2009
Home Page-http://WithDotNet.net
Blog Page-http://JustLikeAMagic.com
Independent software developer, trainer, and technical writer from Egypt born in 1991
 
 
Other popularSectionarticles
    This lesson focuses on how to programmatically turn on the screen saver.
    Published Date : 16/Feb/2010
    By default, arrays are stored in the managed heap with all of the overhead involved and that's because arrays simply are instances of type System.Array that inherits from System.Object. Storing an object into heap means that it will not be removed from the memory until a garbage collection (whether automatic or by calling System.GC.Collect()) occurs. Also, storing it into the heap means suffering from low-performance and the overhead (for the CLR) of storing and retrieving it into and from the h
    Published Date : 16/Feb/2010
    In addition to clearing the console screen, this lesson teaches you some about PInvoking, marshaling, and memory management. Also you will learn additional techniques like clearing a specific portion of the screen, and changing the cursor position. Moreover, you will dig into IL and see how System.Console.Clear() method do it. More than that you will learn how to reverse-engineer a .NET assembly and discover the code inside. In addition, the example shows how to perform I/O operations on cons
    Published Date : 16/Feb/2010
    Swapping mouse buttons means swapping the two buttons, making the right button acts like the left one and vice versa. This is done -for normal users of course- using the Mouse properties dialog in the control panel. See the next figure.
    Published Date : 16/Feb/2010
    Previously, we have talked about how to change screen resolution and color system via DirectX. Today, we are talking about how to change all display settings -not the resolution and color system only- via API. We will change screen resolution (bounds,) color system (bit count,) rotation (orientation,) and refresh rate (frequency) via API with C# and the .NET Framework.
    Published Date : 16/Feb/2010
Comments
There is no comments for this articles.
Leave a Reply
Title:
Display Name:
Email:
(not display in page for the security purphase)
Website:
Message:
Please refresh your screen using Ctrl+F5
If you can't read this number refresh your screen
Please input the anti-spam code that you can read in the image.
^ Scroll to Top