明示的(動的)リンクだから、コマンドプロンプトでDLL?

|

DLLには、プロセスの起動時に読込む静的リンクと、プログラム処理中に動的に読込みと解放を行う明示的リンクが有ります。

ずぼらでめんどくさがり屋には、なるべく簡単な方が宜しいかと。

試しに、C++ ⇒ CのDLL、C ⇒ C++のDLLを動的に呼び出すだけのサンプルを作ってみました。

<注意点>

・C++の文字列(char *)は、デフォルトで定数設定がされているようで、C側で変更するとエラーが発生します。止むを得ず、配列データ(char [])としてC側に渡します。

・VBフォームからの呼出しでも気になっていたのですが、atoi() 関数が上手く機能していないような・・・。(手抜きかよ?)原因は不明です。


お試し環境
  WindowsXP 32bit Edition
  Visual C++ 2008


/*---- C++ ⇒ C の dll 作成 ---------- コマンドライン ---------------------*/

D:\vc2008\dllchk>cl /LD testc.c /link /def:testc.def
(testc.dll を作成)

D:\vc2008\dllchk>cl call_cdll.cpp

/*----------------------------------------------------------------------------*/

/*---- C ⇒ C++ の dll 作成 ---------- コマンドライン ----------------------*/

D:\vc2008\dllchk>cl /LD testpp.cpp /link /def:testpp.def
(testpp.dll を作成)

D:\vc2008\dllchk>cl call_cppdll.c

/*----------------------------------------------------------------------------*/


/*---- C++ ⇒ C の dll 呼出し -------- お試し結果 --------------------------*/

D:\vc2008\dllchk>call_cdll
CPRINT : String from C++ : Visual C++ からの呼び出しです。 - 15
C++PRINT : subc - 0
Cのメッセージ : Hi! Visual C++

/*----------------------------------------------------------------------------*/

/*---- C ⇒ C++ の dll 呼出し -------- お試し結果 --------------------------*/

D:\vc2008\dllchk>call_cppdll
C++PRINT : String from C : Visual C からの呼び出しです。 - 15
CPRINT : subpp - 0
C++のメッセージ : Hello Visual C

/*----------------------------------------------------------------------------*/


/*==== C++ ⇒ C の dll 呼出し ======== お試しソース ========================*/
/*---- testc.def -------------------------------------------------------------*/

LIBRARY testc
EXPORTS
 subc

/*----------------------------------------------------------------------------*/

/*---- testc.c ---------------------------------------------------------------*/

#include <stdio.h>
#include <stdlib.h>   // atoi 関数
#include <string.h>   // strcpy_s 関数

int subc(char *s, int d)
{
    printf("CPRINT : String from C++ : %s - %d\n", s, d);
    strcpy_s(s, d, "Hi! Visual C++");
    return(atoi(s) * d);
}

/*----------------------------------------------------------------------------*/

/*---- call_cdll.cpp ---------------------------------------------------------*/

#include <cstdio>
#include <windows.h>

void main(void)
{
    HINSTANCE hDll;
    int (*func)(char *, int);
    char s[] = "Visual C++ からの呼び出しです。";
//  char *s = "Visual C++ からの呼び出しです。";

    if((hDll = LoadLibrary("testc.dll")) != NULL) {
        if((func = (int (*)(char *, int))GetProcAddress(hDll, "subc")) != NULL) {
            printf("C++PRINT : subc - %d\n", func(s, 15));
            printf("Cのメッセージ : %s\n", s);
            FreeLibrary(hDll);
        } else {
            printf("GetProcAddress 関数の呼び出しに失敗しました。\n");
            FreeLibrary(hDll);
        }
    } else {
        printf("LoadLibrary 関数の呼び出しに失敗しました。\n");
    }
}

/*----------------------------------------------------------------------------*/
/*============================================================================*/


/*==== C ⇒ C++ の dll 呼出し ======== お試しソース ========================*/
/*---- testpp.def ------------------------------------------------------------*/

LIBRARY testpp
EXPORTS
 subpp

/*----------------------------------------------------------------------------*/

/*---- testpp.cpp ------------------------------------------------------------*/

#include <cstdio>
#include <cstdlib>   // atoi 関数
#include <cstring>   // strcpy_s 関数

extern "C" int subpp(char *s, int d)
{
    printf("C++PRINT : String from C : %s - %d\n", s, d);
    strcpy_s(s, (unsigned int)d, "Hello Visual C");
    return(atoi(s) * d);
}

/*----------------------------------------------------------------------------*/

/*---- call_cppdll.c ---------------------------------------------------------*/

#include <stdio.h>
#include <windows.h>

void main(void)
{
    HINSTANCE hDll;
    int (*func)(char *, int);
    char *s = "Visual C からの呼び出しです。";

    if((hDll = LoadLibrary("testpp.dll")) != NULL) {
        if((func = (int (*)(char *, int))GetProcAddress(hDll, "subpp")) != NULL) {
            printf("CPRINT : subpp - %d\n", func(s, 15));
            printf("C++のメッセージ : %s\n", s);
            FreeLibrary(hDll);
        } else {
            printf("GetProcAddress 関数の呼び出しに失敗しました。\n");
            FreeLibrary(hDll);
        }
    } else {
        printf("LoadLibrary 関数の呼び出しに失敗しました。\n");
    }
}

/*----------------------------------------------------------------------------*/
/*============================================================================*/