Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 6 additions & 5 deletions examples/basic/unsafes/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,9 @@

このディレクトリには以下のサンプルがあります。

| file | example name | note |
| -------------------- | ----------------- | --------------------------------------- |
| unsafe_sizeof.go | unsafe_sizeof | unsafe.Sizeof() についてのサンプルです. |
| unsafe_string.go | unsafe_string | unsafe.String() のサンプルです. |
| unsafe_stringdata.go | unsafe_stringdata | unsafe.StringData() のサンプルです. |
| file | example name | note |
| ---------------------- | ------------------- | -------------------------------------------------------------------- |
| unsafe_sizeof.go | unsafe_sizeof | unsafe.Sizeof() についてのサンプルです. |
| unsafe_string.go | unsafe_string | unsafe.String() のサンプルです. |
| unsafe_stringdata.go | unsafe_stringdata | unsafe.StringData() のサンプルです. |
| unsafe_pointer_cast.go | unsafe_pointer_cast | unsafeパッケージを用いてポインタを任意の型にキャストするサンプルです |
1 change: 1 addition & 0 deletions examples/basic/unsafes/examples.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,4 +16,5 @@ func (r *register) Regist(m mapping.ExampleMapping) {
m["unsafe_sizeof"] = Sizeof
m["unsafe_string"] = UnsafeString
m["unsafe_stringdata"] = UnsafeStringData
m["unsafe_pointer_cast"] = PointerCast
}
46 changes: 46 additions & 0 deletions examples/basic/unsafes/unsafe_pointer_cast.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
package unsafes

import (
"fmt"
"unsafe"
)

// PointerCast は、unsafeパッケージを用いてポインタを任意の型にキャストするサンプルです。
//
// unsafe.Pointer は、C言語でいう (void *) と同じものとなる。
// C言語において、(void *) は何にでも成れるのと同様に unsafe.Pointer はGoでもどの型にもキャスト出来る。
// ただし、unsafeパッケージを利用する時点でGoの持つ安全性を無くすことに注意が必要。
//
// REFERENCES:
// - https://pkg.go.dev/unsafe@go1.25.3#Pointer
func PointerCast() error {
var (
value int = 0x01020304
ptr unsafe.Pointer
cast1 *byte
cast2 *[4]byte
)
// 元の値をunsafe.Pointerにする
ptr = unsafe.Pointer(&value)

// C言語でいう (char *)ptr; のような変換
cast1 = (*byte)(ptr)

// 明示的な配列のポインタへの変換
cast2 = (*[4]byte)(ptr)

// 値を確認 (cast1)
// *cast1 は最初の1バイトのみを参照する (リトルエンディアン環境では 0x04)
// 後続バイトにアクセスするには unsafe.Add() または uintptrを使ったポインタ演算 などを使用する必要がある
fmt.Printf("cast1: 1バイト目: 0x%02X\n", *cast1)
fmt.Println("---------------------------------")

// 値を確認 (cast2)
// *[4]byte 型なので配列として全4バイトに直接アクセス可能
// メモリレイアウトはエンディアンに依存する(リトルエンディアンでは逆順)
for i, v := range cast2 {
fmt.Printf("cast2: %dバイト目: 0x%02X\n", i, v)
}

return nil
}