ホームページ  >  記事  >  バックエンド開発  >  Go で `ioctl()` を実装するときに発生する「無効な引数」エラーを解決する方法

Go で `ioctl()` を実装するときに発生する「無効な引数」エラーを解決する方法

Barbara Streisand
Barbara Streisandオリジナル
2024-11-21 17:22:11917ブラウズ

How to Resolve

Go での IOCTL 実装

質問:

ioctl() を含む C コードの変換についてGo に移行すると、次の C を変換するときに問題が発生します。コード:

#define MAJOR_NUM 100
#define IOCTL_MBOX_PROPERTY _IOWR(MAJOR_NUM, 0, char *)
static int mbox_property(int file_desc, void *buf){
   int ret_val = ioctl(file_desc, IOCTL_MBOX_PROPERTY, buf);
   return ret_val;
}

対応する Go コード:

func mBoxProperty(f *os.File, buf [256]int64) {
        err := Ioctl(f.Fd(), IOWR(100, 0, 8), uintptr(unsafe.Pointer(&buf[0])))

        if err != nil {
                log.Fatalln("mBoxProperty() : ", err)
        }

}

func Ioctl(fd, op, arg uintptr) error {
        _, _, ep := syscall.Syscall(syscall.SYS_IOCTL, fd, op, arg)
        if ep != 0 {
                return syscall.Errno(ep)
        }
        return nil
}

func IOWR(t, nr, size uintptr) uintptr {
        return IOC(IocRead|IocWrite, t, nr, size)
}
func IOC(dir, t, nr, size uintptr) uintptr {
        return (dir << IocDirshift) | (t << IocTypeshift) | (nr << IocNrshift) | (size << IocSizeshift)
}

は、「無効な引数」エラーを引き起こします。潜在的な問題は何ですか?

回答:

問題を修正するには、次の点を考慮してください:

  • 「golang.org/x/sys/unix」の ioctl() のラッパーを利用します。特に、unix.IoctlSetInt がユースケースに適している可能性があります。
  • 小さなメモリ バッファをカーネルに渡すときは注意してください。 Go のガベージ コレクターは、未使用とみなしたオブジェクトを解放し、場合によっては移動することもできます。これにより、カーネルの操作と Go コードの期待との間に矛盾が生じる可能性があります。
  • cgo を使用して適切なバッファーに malloc() する適度な拡張機能を記述し、それを ioctl に渡すことを検討してください。 malloc() によって割り当てられたメモリはガベージ コレクションの対象ではないため、前述の問題が軽減されます。

以上がGo で `ioctl()` を実装するときに発生する「無効な引数」エラーを解決する方法の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。