title: Call C++ dll from with Delphi
body: <p>My goal is to call a function written in C++ (with a C interface) from within Delphi (RAD Studio XE6). In the end, the dll will be generated by Visual Studio 2013, but I've tried to start with generating the Dll from RAD Studio XE6.</p>
  
  <p>So, I have created a Dll project in Rad Studio (Using VC++ style Dll). The file is here</p>
  
  <pre><code>#include &lt;vcl.h&gt;
  #include &lt;windows.h&gt;
  
  #pragma hdrstop
  #pragma argsused
  
  int WINAPI DllEntryPoint(HINSTANCE hinst, unsigned long reason, void* lpReserved)
  {
      return 1;
  }
  
  extern "C" int next(int n) {
      return n + 1;
  }
  </code></pre>
  
  <p>It compiles as a Dll. On the Delphi side, the code is as below:</p>
  
  <pre><code>program Project1;
  
  {$APPTYPE CONSOLE}
  
  {$R *.res}
  
  uses
    System.SysUtils, Windows;
  function next(a: Int32): Int32; cdecl;
    external 'Project3.dll';
  var
    a: Int32;
  begin
    try
      a := 3;
      Writeln('Hello world!', next(a));
      sleep(3000);
    except
      on E: Exception do
        Writeln(E.ClassName, ': ', E.Message);
    end;
  end.
  </code></pre>
  
  <p>The project does compile but does not run. It gives the following error:</p>
  
  <pre><code>*** A stack buffer overrun occurred in "C:\...\Debug\Project1.exe"
  </code></pre>
  
  <p>It fails on the following assembly line</p>
  
  <pre><code>mov eax,[edi]
  </code></pre>
  
  <p>I have tried to change cdecl to std call, pascal or register. But nothing works.</p>
  
  <p>Solution: Thanks to Rudy, the following code does work. First the C++ side:</p>
  
  <pre><code>#include &lt;vcl.h&gt;
  #include &lt;windows.h&gt;
  
  #pragma hdrstop
  #pragma argsused
  
  int WINAPI DllEntryPoint(HINSTANCE hinst, unsigned long reason, void* lpReserved)
  {
      return 1;
  }
  
  extern "C" __declspec(dllexport) int __stdcall next(int n) {
      return n + 1;
  }
  </code></pre>
  
  <p>and then the Delphi side.</p>
  
  <pre><code>program Project1;
  
  {$APPTYPE CONSOLE}
  
  {$R *.res}
  
  uses
    System.SysUtils, Windows;
  function next(a: Int32): Int32; stdcall;
    external 'Project3.dll';
  var
    a: Int32;
  begin
    try
      a := 3;
      Writeln('Hello world!', next(a));
      sleep(3000);
    except
      on E: Exception do
        Writeln(E.ClassName, ': ', E.Message);
    end;
  end.
  </code></pre>