すいません、VB4しかやってないんです、VBAはやったけど(ぼそ) チラシの裏だって立派な書き込み空間なんだからねっ!資源の有効活用なんだからねっ!とか偉そうに言ってるけど、実は色々と書き残したいだけ

だからなに? どうしろと? くるみサイズの脳みそしかないあやしいジャンガリアンベムスターがさすらう贖罪蹂躙(ゴシックペナルティ)

ホーム 連絡をする 同期する ( RSS 2.0 ) Login
投稿数  632  : 記事  35  : コメント  11677  : トラックバック  143

ニュース


片桐 継 は
こんなやつ

かたぎり つぐ ってよむの

大阪生まれ河内育ちなんだけど
関東に住みついちゃったの
和装着付師だったりするの
エセモノカキやってたりするの
VBが得意だったりするの
SQL文が大好きだったりするの
囲碁修行中だったりするの
ボトゲ好きだったりするの
F#かわいいよF#

正体は会った人だけ知ってるの

空気読まなくてごめんなさいなの


わんくまリンク

C#, VB.NET 掲示板
C# VB.NET掲示板

わんくま同盟
わんくま同盟Blog


WindowsでGo言語
WindowsでGo言語


ネット活動


SNSは疲れました

記事カテゴリ

書庫

日記カテゴリ

ギャラリ

イベント活動

プログラムの活動

Sorry, This post is Japanese Only.

I'm verifying the memory allocation of Go Launguage on WindowsPort using Windbg.

String type of Go Launguage is allocated using pointer (LongHex type) and  Length (LongUnsignedHex type) .

まずはサンプルソース。

package main

import(
 "fmt"
 "bufio"
 "os"
 "unsafe" 
)

// 構造体を定義
type H struct {
  背番号 int
  カナ byte
  名前 string
  住んでる所 string
  性格 string
 }

// main関数
func main(){

 // 構造体をそれぞれ初期化
 oHanaaruki := H{1,'o', "オオハナアルキ", "地上", "ちょっと凶暴"}
 mHanaaruki := H{2,'m', "マンモスハナアルキ", "地上", "のんびり"}
 dHanaaruki := H{3,'d', "ダンボハナアルキ", "空中", "ぱたぱた系"}
 jHanaaruki := H{4,'j', "ジェットハナアルキ", "空中", "ビュンビュン系"}
 bHanaaruki := H{5,'b', "バニラ・ランモドキ", "樹上", "お色気派"}
 
 // 構造体のサイズを確認
 fmt.Printf("構造体メモリサイズ:%d\n",unsafe.Sizeof(H{})) 

 // 構造体を配列に格納
 hs := []H{oHanaaruki,mHanaaruki}
 
 // 構造体のポインタを配列に格納
 hsp := []*H{ &dHanaaruki, &jHanaaruki, &bHanaaruki}

 // 配列のサイズを確認
 fmt.Printf("構造体メモリ展開個数:%d\n",len(hs))
 fmt.Printf("構造体ポインタ展開個数:%d\n",len(hsp))

 //  構造体を初期化
 h := new(H)

 // 構造体へのポインタを初期化
 var hp *H 
 hpt := new(*H) 
 
 //  それぞれがどう割り当てられたかを確認
 fmt.Printf("フツーの初期化:%d\n",h)
 fmt.Printf("ポインタの初期化:%d\n",hp)
 fmt.Printf("ポインタの初期化:%d\n",hpt)
 fmt.Printf("構造体メモリアドレス:%p\n",&hs)
 fmt.Printf("構造体ポインタアドレス:%p\n",hsp)
 fmt.Printf("オオハナルキのポインタ:%p\n",&oHanaaruki)
 fmt.Printf("ランモドキのポインタ:%p\n",&bHanaaruki)
 fmt.Printf("ランモドキカナのポインタ:%p\n",&bHanaaruki.カナ)
 fmt.Printf("ランモドキ名前のポインタ:%p\n",&bHanaaruki.名前)
 fmt.Printf("ランモドキ住んでる所のポインタ:%p\n",&bHanaaruki.住んでる所)
 fmt.Printf("ランモドキ性格のポインタ:%p\n",&bHanaaruki.性格)
 
 ins := bufio.NewReader(os.Stdin)
 for{
      line, err := ins.ReadString('\n') 
      if err == os.EOF { 
  fmt.Printf(";;;End\n")
         break 
      } 
  fmt.Printf(";;;%s",line)
   } 
 
}

構造体を定義して、それぞれを配列にしたり、初期化したり、その時にどんなふうに、メモリが配置されてるかを確認してみる。

動かすと

image

62行目移行で、Ctl+zが入力されるまでずっと待ってると言う動きになっているので、各変数をメモリ展開した後でWindbgを起動、このプロセスを捕まえて調査開始。

Menu(File) > Attach Process > Select main.exe

image

main.exe を探してAttach

Process And Threads Window を起動

image

メインプロセスには、このプログラムにはChannelは存在しないので、二つのスレッドが存在。

(There is One Process and Two Threads. Because this process has no Channel Type)

ここで次はMemoryWindowを起動して、

「ポインタの初期化:0x570018」のアドレスを探ると

image 

アドレスの指す先は「0x0000」だけれども、確かに、領域が確保できてるのが判るのね。

それじゃ、中身のある、構造体配列はどうなってるんだろう。

「構造体メモリアドレス:0x5753f0」を探ってみると

image 

そこにはまた、意味ありげなアドレスが。そこで、そのアドレスに飛んでみると、

 image

 

むむ、これは?

ここで構造体の定義を考えてみると、int型、byte型、String型をそれぞれ持たせていたはず。

そこで、最後のPrintf結果から、それぞれのアドレスの差異を計算すると

ランモドキのポインタ:0x5737a0
ランモドキカナのポインタ:0x5737a4
ランモドキ名前のポインタ:0x5737a8
ランモドキ住んでる所のポインタ:0x5737b0
ランモドキ性格のポインタ:0x5737b8

int=(0x5737a4)-(0x5737a4)=4Byte、byte=(0x5737a4)-(0x5737a8)=4Byte、String=(0x5737a8)-(0x5737b0)=8Byte のサイズ、と考えることができる。だから構造体のトータルサイズは32Byte、と計算されてたんだぁ、と納得もできるよね。

ちなみに、今表示しているWindbgのMemoryWindowではLong Hex モードなので、一つの塊が4Byte、つまり、ここに確かに構造体の中身が展開されているのは間違いなさそう。

でもString型は文字列。どうして全部8Byteなんだろ? これは、どこかにStringの中身本体が展開されていて、ここにはそのアドレスだけが展開されているって考えられるので、早速、そのアドレスへ飛んでみる。

image

それっぽいよねぇ、文字列で「オオハナアルキ」は7文字。e3を区切りとして数えると7個あって、最初の二つは同じ値、5番目の値は、1番目の値の8Byte先の数字。2Byteと考えると、5番目を基準に、4個先の文字コードの文字が1番目にいるんだもの。これは、確定じゃね?

そこで、ちょっと一つ前に戻って、

image

再度、構造体本体のアドレスに戻って、今度は「Long Unsigned Hex」モードで表示。すると、今度は先ほどのString型を展開したアドレスの後ろに意味ありげな数字が。

Go言語ではString型の中身はすべてUnicodeであつかうという決まりがあるので、このアドレス位置から指定された数字の分だけ値をとりだして、空白に%を埋めて、URLデコードにかけてみると

「%e3%82%aa%e3%82%aa%e3%83%8f%e3%83%8a%e3%82%a2%e3%83%ab%e3%82%ad」→「オオハナアルキ」

というわけで、オオハナアルキを発見

Go言語にはクラスの概念は無いけれども、ANSI-Cの時代から培われてきたメモリアロケートの考え方がしっかりと生きていて、全ての展開アドレスを自プロセスの中できちんと完結させられるように仕組みがなっている、と考えていいと思う。

結論:

「Go言語の初期化済みString型は、LongHexのメモリアドレスポインタとLongUnsignedHexのサイズで構成されている」

投稿日時 : 2010年7月25日 11:11

コメント

# 
Twitter Trackbacks for

Go?????????????????????????????????~Windows??????????????????????????????????????????
[wankuma.com]
on Topsy.com
2010/07/25 11:52 Pingback/TrackBack

Twitter Trackbacks for

Go?????????????????????????????????~Windows??????????????????????????????????????????
[wankuma.com]
on Topsy.com


# Oakley Holbrook 2013/03/13 12:21 http://oakleyfrogskinsholbrookradar.blinkweb.com/
You can't go in no matter who you are.Did you miss the bus? I found him seated on the bench.I didn't realize how much this meant to youNeither of the men spoke.I regret to inform you that we are unable to offer you employment.I regret to inform you that we are unable to offer you employment.You'd better let her alone.Supper is ready at six.I have a headache, and she has a stomachache.

Post Feedback

タイトル
名前
Url:
コメント