C#中通過DllImport使用 Win32 API

來源:互聯網
上載者:User

.net 架構程式可以通過靜態 DLL 進入點的方式來訪問機器碼庫。DllImport 屬性用於指定包含外部方法的實現的dll 位置。

DllImport 屬性定義如下:

namespace System.Runtime.InteropServices
{
 [AttributeUsage(AttributeTargets.Method)]
 public class DllImportAttribute: System.Attribute
 {
public DllImportAttribute(string dllName) {...}
public CallingConvention CallingConvention;
public CharSet CharSet;
public string EntryPoint;
public bool ExactSpelling;
public bool PreserveSig;
public bool SetLastError;
public string Value { get {...} }
 }
}

說明:

1、DllImport只能放置在方法聲明上。
 2、DllImport具有單個定位參數:指定包含被匯入方法的 dll 名稱的 dllName 參數。
3、DllImport具有五個具名引數:
 a、CallingConvention 參數指示進入點的呼叫慣例。如果未指定 CallingConvention,則使用預設值 CallingConvention.Winapi。
 b、CharSet 參數指示用在進入點中的字元集。如果未指定 CharSet,則使用預設值 CharSet.Auto。
 c、EntryPoint 參數給出 dll 中進入點的名稱。如果未指定 EntryPoint,則使用方法本身的名稱。
 d、ExactSpelling 參數指示 EntryPoint 是否必須與指示的進入點的拼字完全符合。如果未指定 ExactSpelling,則使用預設值 false。
 e、PreserveSig 參數指示方法的簽名應當被保留還是被轉換。當簽名被轉換時,它被轉換為一個具有 HRESULT 傳回值和該傳回值的一個名為 retval 的附加輸出參數的簽名。如果未指定 PreserveSig,則使用預設值 true。
 f、SetLastError 參數指示方法是否保留 Win32"上一錯誤"。如果未指定 SetLastError,則使用預設值 false。

4、它是一次性屬性類。
5、此外,用 DllImport 屬性修飾的方法必須具有 extern 修飾符。

下面是 C# 調用 Win32 MessageBox 函數的樣本:

using System;
using System.Runtime.InteropServices;
class MainApp
{

//通過DllImport引用user32.dll類。MessageBox來自於user32.dll類
 [DllImport("user32.dll", EntryPoint="MessageBox")]
 public static extern int MessageBox(int hWnd, String strMessage, String strCaption, uint uiType);
 public static void Main()
 {
MessageBox( 0, "您好,這是 PInvoke!", ".net", 0 );
 }
}

物件導向的程式設計語言幾乎都用到了抽象類別這一概念,抽象類別為實現抽象事物提供了更大的靈活性。C#也不例外, C#通過覆蓋虛介面的技術深化了抽象類別的應用。欲瞭解這方面的知識,請看下一節-覆蓋虛介面

這裡講述的是C#調用標準動態庫的問題, 在我以前的檔案中講到過, C#調用Win32API, 原理是一樣的. 這裡我詳細講解用C寫一個標準的動態庫, 然後讓C#調用. (本篇適合初學者, 中間沒有任何冗餘代碼, 簡潔明了)
軟體環境: VC6.0(當然其他版本的VC5也可以)
1.製作標準動態庫
__declspec(dllexport) int __cdecl add(int, int);//這一句是聲明動態庫輸出一個可供外不調用的函數原型.
int add(int a,int b) {//實現這個函數
return a+b;
}
以上簡單3行代碼,聲明一個add的方法, 輸入參數是兩個int參數,返回這兩個數之和. 儲存為MyLib.c
然後執行編譯命令.
H:\XSchool\C#-School\HowTo>cl /LD MyLib.c
Microsoft (R) 32-bit C/C++ Optimizing Compiler Version 12.00.8168 for 80x86
Copyright (C) Microsoft Corp 1984-1998. All rights reserved.

MyLib.c
Microsoft (R) Incremental Linker Version 6.00.8447
Copyright (C) Microsoft Corp 1992-1998. All rights reserved.

/out:MyLib.dll
/dll
/implib:MyLib.lib
MyLib.obj
Creating library MyLib.lib and object MyLib.exp

確信有以上輸出, 說明編譯成功產生了動態庫.

2.編寫C-Sharp程式調用該動態庫
using System;
using System.Runtime.InteropServices;//這是用到DllImport時候要引入的包

public class InvokeDll {
[DllImport("MyLib.dll", CharSet=CharSet.Auto)]
static extern int add(int a,int b);//聲明外部的標準動態庫, 跟Win32API是一樣的.

public static void Main() {
Console.WriteLine(add(10,30));
}
}
儲存為InvokeDll.cs檔案, 與MyLib.dll置於同一目錄, 編譯該檔案.
H:\XSchool\C#-School\HowTo>csc invokedll.cs
將產生Invokedll.exe, 可以執行該檔案.
以上是C-Sharp調用標準動態庫的全過程, 本來覺得很簡單的東西, 一直都沒有想寫, 碰巧今日遇一朋友問及此事, 就順便寫了下來.

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.