Click here to Skip to main content
15,891,033 members
Articles / Programming Languages / C++/CLI

C++ Interop is for the Performance Minded Developer

Rate me:
Please Sign up or sign in to vote.
4.88/5 (18 votes)
2 Jan 2007CPOL10 min read 76.1K   681   47  
Highlighting interoperability support provided by C++ and analysis of performance
using System;
using System.Collections.Generic;
using System.Text;
using System.Runtime.InteropServices;

namespace CSharpCon
{
 using CppMixed;

 class Program
 {
  [DllImport("Kernel32.dll")]
  private static extern bool QueryPerformanceCounter(out long lpPerformanceCount);

  [DllImport("Kernel32.dll")]
  private static extern bool QueryPerformanceFrequency(out long lpFrequency);

  [DllImport("CppMixed.dll")]
  private static extern void funcCalc (out int count, out double answer, out double mean);

  [DllImport("CppMixed.dll", SetLastError = true, CharSet = CharSet.Auto)]
  private static extern void funcInfo([MarshalAs(UnmanagedType.LPStr)]StringBuilder lpBuffer, out int cnt);


  static double ManagedManaged(int loop)
  {
   long start, stop, freq;
  
   QueryPerformanceFrequency(out freq);
   QueryPerformanceCounter(out start);

   for (int z = 0; z < loop; z++)
   {
    Simple sim = new Simple();
    Results res = new Results();

    sim.calc(res);
    //Console.WriteLine("Simple calc time {0}", time);
    //Console.WriteLine("Count = {0} Sum = {1}  Mean = {2}", res._count, res._answer, res._mean);
   }

   QueryPerformanceCounter(out stop);
   double time = (double)(stop - start) / (double)freq;

   return time;
  }
  static double NonBlitManaged(int loop)
  {
   long start, stop, freq;

   QueryPerformanceFrequency(out freq);
   QueryPerformanceCounter(out start);

   for (int z = 0; z < loop; z++)
   {
    Simple sim = new Simple();
    NonBlittable nb = new NonBlittable();

    sim.getTextDescription(nb);
    //Console.WriteLine("String {0} ; Length = {1}", nb._name, nb._len);
   }

   QueryPerformanceCounter(out stop);
   double time = (double)(stop - start) / (double)freq;
   
   return time;
  }

  static double NonBlitUnmanaged(int loop)
  {
   long start, stop, freq;

   QueryPerformanceFrequency(out freq);
   QueryPerformanceCounter(out start);

   for (int z = 0; z < loop; z++)
   {
    int c = 100;
    StringBuilder s = new StringBuilder(c);
    funcInfo(s, out c);
    
    //Console.WriteLine("String = {0} ,Len = {1}", s, c);
   }

   QueryPerformanceCounter(out stop);
   double time = (double)(stop - start) / (double)freq;
   
   return time;
  }
  static double ManagedUnmanaged(int loop)
  {
   long start, stop, freq;
  
   QueryPerformanceFrequency(out freq);
   QueryPerformanceCounter(out start);

   for (int z = 0; z < loop; z++)
   {
    int nCount = 0;
    double dblAns = 0.0, dblMean = 0.0;

    funcCalc(out nCount, out dblAns, out dblMean);

    //Console.WriteLine("C Function calc time {0}", time);
    //Console.WriteLine("Count = {0} Sum = {1}  Mean = {2}", nCount, dblAns, dblMean);
   }

   QueryPerformanceCounter(out stop);
   double time = (double)(stop - start) / (double)freq;

   return time;
  }

  static void Main(string[] args)
  {
   int glbLoop = 1;
   if (args.Length > 0)
     glbLoop = Convert.ToInt32(args[0]);

   Console.WriteLine("Number of call iterations equals {0}", glbLoop);
   Console.WriteLine(""); 

   int loop = 10;

   // The data returned by both functions are blittable data types.
   // The C# data is returned through a ref class whereas the C function returns
   // results via func parameter references
   Console.WriteLine("Blittable data types");
   Console.WriteLine("Reference class calc time, C-Func calc time");
    
   for (int x = 0; x < loop; x++)
   {
    /////////////////////////////////////////////////////
    // calling a Managed object from the mixed mode DLL
    double mmtime = ManagedManaged(glbLoop);

    ////////////////////////////////////////////////////
    // calling native C function using P/Invoke
    double mutime = ManagedUnmanaged(glbLoop);

    Console.WriteLine("{0}, {1}", mmtime, mutime);
   }
   Console.WriteLine("");
   
   //////////////////////////////////////////////////////////////////
   // communicating data via a structure with non-blittable types
   Console.WriteLine("Non-blittable data types");
   Console.WriteLine("Reference class calc time, C-Func calc time");

   for (int x = 0; x < loop; x++)
   {
    /////////////////////////////////////////////////////
    // calling a Managed object from the mixed mode DLL
    double nbmtime = NonBlitManaged(glbLoop);

    ////////////////////////////////////////////////////
    // calling native C function using P/Invoke
    double nbutime = NonBlitUnmanaged(glbLoop);

    Console.WriteLine("{0}, {1}", nbmtime, nbutime);
   }
   Console.WriteLine("");

  }
 }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Engineer
United States United States
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions