5
Help us understand the problem. What are the problem?

posted at

updated at

Go言語でDLLの関数(システムコール)を呼び出す

★★★2021/11/23追記★★★

mksyscall_windows.goというツールを使っていますが、あまりちゃんと認識していませんでした。
(今も深くは理解していませんが)このツール自体名前からして、Windowsのシステムコールを作るものですね。
「任意のDLLの関数を呼び出す方法」としては不適切だったため、タイトルを変更しました。


こちらを参考にさせていただきました:Big Sky :: golang で型付きで DLL を呼び出す方法
―――――――――――

まず、以下を定義したsyscall_windows.goというファイルを作成しました。

  • go generate向けの、ツールmksyscall_windows.goで中間コードzsyscall_windows.goを生成する定義
  • mksyscall_windows.go向けの、DLL関数をラップするGo言語関数の定義
syscall_windows.go
package main

//go:generate go run $GOROOT/src/syscall/mksyscall_windows.go -output zsyscall_windows.go syscall_windows.go

//sys messageBox(hWnd syscall.Handle, lpText string, lpCaption string, uType uint32) (dwRet uint32, err error) = User32.MessageBoxW

go generateを実行すると、以下のようなコードが生成されます。

zsyscall_windows.go(抜粋)
func messageBox(hWnd syscall.Handle, lpText string, lpCaption string, uType uint32) (dwRet uint32, err error) {
    var _p0 *uint16
    _p0, err = syscall.UTF16PtrFromString(lpText)
    if err != nil {
        return
    }
    var _p1 *uint16
    _p1, err = syscall.UTF16PtrFromString(lpCaption)
    if err != nil {
        return
    }
    return _messageBox(hWnd, _p0, _p1, uType)
}

func _messageBox(hWnd syscall.Handle, lpText *uint16, lpCaption *uint16, uType uint32) (dwRet uint32, err error) {
    r0, _, e1 := syscall.Syscall6(procMessageBoxW.Addr(), 4, uintptr(hWnd), uintptr(unsafe.Pointer(lpText)), uintptr(unsafe.Pointer(lpCaption)), uintptr(uType), 0, 0)
    dwRet = uint32(r0)
    if dwRet == 0 {
        if e1 != 0 {
            err = errnoErr(e1)
        } else {
            err = syscall.EINVAL
        }
    }
    return
}

―★疑問★――――――
dwRet(異常時は0)がうまいことエラーハンドリングされているように見えます。
正常時に0となる関数はどうするのでしょう。

★★★2021/11/23追記★★★
Windowsのシステムコールを扱う関数なので、DWRODが返る時点で異常時が0、という扱いなのかも。
―――――――――――

あとは生成されたmessageBox()を呼び出せばOKです。

main.go
package main

func main() {
    messageBox(0, "message", "title", 0)
}

実行するとメッセージボックスが表示されました。

image.png

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Sign upLogin
5
Help us understand the problem. What are the problem?