ActiveBasic 4.21.00 で RegQueryValueEx を使った REG_SZ 値の読取りがうまくいきません。
DEBUG で見ると lpcbData は受け取っていますが lpData が受け取れないようです。
REG_DWORD は読取れます。また RegSetValueEx での書込みもできます。
うまく読取れる例示がありましたら教えて下さい。
RegQueryValueEx での REG_SZ 値の読取り
いろいろ試してはいるんですが
メモリ確保はやっています。
------------------------
Dim hKey As HKEY
Dim phkResult As HKEY
Dim lpSubKey As String
Dim ValueName As String
Dim lpReserved As DWord
Dim RegType As DWord
Dim lpType As DWordPtr
Dim lpData As VoidPtr
Dim lpcbData As DWordPtr
Dim Company As String
Dim CompanyL As Long
hKey = HKEY_LOCAL_MACHINE
lpSubKey = "SOFTWARE\Microsoft\Windows NT\CurrentVersion"
If RegOpenKeyEx(hKey, lpSubKey, 0, KEY_READ, phkResult) = ERROR_SUCCESS Then
ValueName = "RegisteredOrganization"
lpReserved = 0
RegType = REG_SZ
lpType = VarPtr(RegType)
lpData = VarPtr(Company)
lpcbData = VarPtr(CompanyL)
If RegQueryValueEx(phkResult,ValueName,lpReserved,lpType,lpData,lpcbData)= ERROR_SUCCESS Then
Company = String$(CompanyL," ")
If RegQueryValueEx(phkResult,ValueName,lpReserved,lpType,lpData,lpcbData)= ERROR_SUCCESS Then
Else Goto *Read_error
End If
Else Goto *Read_error
End If
End If
RegCloseKey(phkResult)
------------------------
エラーは出ないのですが Company には何も読み込まれていません。
CompanyL には文字数が入ってきます。
RegOpenKeyEx のパラメータを色々変えてみましたが(NULL指定とか)うまくいきません。
読取るレジストリの値が REG_DWORD の場合はうまくいくんですが。
------------------------
Dim hKey As HKEY
Dim phkResult As HKEY
Dim lpSubKey As String
Dim ValueName As String
Dim lpReserved As DWord
Dim RegType As DWord
Dim lpType As DWordPtr
Dim lpData As VoidPtr
Dim lpcbData As DWordPtr
Dim Company As String
Dim CompanyL As Long
hKey = HKEY_LOCAL_MACHINE
lpSubKey = "SOFTWARE\Microsoft\Windows NT\CurrentVersion"
If RegOpenKeyEx(hKey, lpSubKey, 0, KEY_READ, phkResult) = ERROR_SUCCESS Then
ValueName = "RegisteredOrganization"
lpReserved = 0
RegType = REG_SZ
lpType = VarPtr(RegType)
lpData = VarPtr(Company)
lpcbData = VarPtr(CompanyL)
If RegQueryValueEx(phkResult,ValueName,lpReserved,lpType,lpData,lpcbData)= ERROR_SUCCESS Then
Company = String$(CompanyL," ")
If RegQueryValueEx(phkResult,ValueName,lpReserved,lpType,lpData,lpcbData)= ERROR_SUCCESS Then
Else Goto *Read_error
End If
Else Goto *Read_error
End If
End If
RegCloseKey(phkResult)
------------------------
エラーは出ないのですが Company には何も読み込まれていません。
CompanyL には文字数が入ってきます。
RegOpenKeyEx のパラメータを色々変えてみましたが(NULL指定とか)うまくいきません。
読取るレジストリの値が REG_DWORD の場合はうまくいくんですが。
Re: いろいろ試してはいるんですが
CompanyはString型なので、ポインタはStrPtr関数で取得します。[lpData = VarPtr(Company) の行のこと]
また、String型のポインタは文字列を代入するたびに変わります。そのため、別の変数にポインタを格納しておくのはオススメできません。引数に直接StrPtr関数で取得したポインタを指定するか、(コンパイルが通るなら)単純に文字列変数をそのまま引数に指定するほうが安全です。
※どうしても変数にポインタを格納する場合は、そのポインタを使う関数の直前にしておいたほうがいいでしょう
それから、データの長さだけがほしいときは、lpDataパラメータはNULLにしておいたほうがいいでしょう。
以上を踏まえると…
こんな感じでしょうか?(当方の環境で動作確認)
また、String型のポインタは文字列を代入するたびに変わります。そのため、別の変数にポインタを格納しておくのはオススメできません。引数に直接StrPtr関数で取得したポインタを指定するか、(コンパイルが通るなら)単純に文字列変数をそのまま引数に指定するほうが安全です。
※どうしても変数にポインタを格納する場合は、そのポインタを使う関数の直前にしておいたほうがいいでしょう
それから、データの長さだけがほしいときは、lpDataパラメータはNULLにしておいたほうがいいでしょう。
以上を踏まえると…
コード: 全て選択
Dim hKey As HKEY
Dim phkResult As HKEY
Dim lpSubKey As String
Dim ValueName As String
Dim lpReserved As DWord
Dim RegType As DWord
Dim lpType As DWordPtr
Dim lpcbData As DWordPtr
Dim Company As String
Dim CompanyL As Long
hKey = HKEY_LOCAL_MACHINE
lpSubKey = "SOFTWARE\Microsoft\Windows NT\CurrentVersion"
If RegOpenKeyEx(hKey, lpSubKey, 0, KEY_READ, phkResult) = ERROR_SUCCESS Then
ValueName = "RegisteredOrganization"
lpReserved = 0
RegType = REG_SZ
lpType = VarPtr(RegType)
lpcbData = VarPtr(CompanyL)
If RegQueryValueEx(phkResult,ValueName,lpReserved,lpType,NULL,lpcbData)= ERROR_SUCCESS Then
Company = String$(CompanyL," ")
If RegQueryValueEx(phkResult,ValueName,lpReserved,lpType,StrPtr(Company),lpcbData)= ERROR_SUCCESS Then
Else Goto *Read_error
End If
Else Goto *Read_error
End If
End If
RegCloseKey(phkResult)
[hira]
http://hira.hopto.org/
http://hira.hopto.org/
StrPtrを使うんですね
ありがとうございます。
String型の場合はStrPtr関数を使うんですね。
Win32プログラミング講座(Step28)とActiveBasicのHELPを見て、全ての型でVarPtrが使えるものと思い込んでいました。
ご指摘のとおりStrPtr(lpData)ではうまくいきました。
また、RegQueryValueEx では lpData として文字列変数をそのまま使うとうまくいきません。
エラーは出ませんが変数には読み込めませんでした。
RegSetValueEx では lpData として文字列変数をそのまま使ってもOKです。
このへんは仕様なんでしょうか。
56才、孫1人ですがプログラミング言語はまだ初心者です。
これからもよろしくお願いします。
String型の場合はStrPtr関数を使うんですね。
Win32プログラミング講座(Step28)とActiveBasicのHELPを見て、全ての型でVarPtrが使えるものと思い込んでいました。
ご指摘のとおりStrPtr(lpData)ではうまくいきました。
また、RegQueryValueEx では lpData として文字列変数をそのまま使うとうまくいきません。
エラーは出ませんが変数には読み込めませんでした。
RegSetValueEx では lpData として文字列変数をそのまま使ってもOKです。
このへんは仕様なんでしょうか。
56才、孫1人ですがプログラミング言語はまだ初心者です。
これからもよろしくお願いします。
Re: StrPtrを使うんですね
確かに、当方でも文字列変数を直接指定すると結果が取れませんでした。
以前はBytePtr引数だけでなくVoidPtr引数でもいけた気がしたんですが…。すみません、StrPtr使ってやってください(^^;;
どちらにしても、エラーにならないのはデバッグするときに無駄に時間を使わせますから、バグとして報告しておきます。
以前はBytePtr引数だけでなくVoidPtr引数でもいけた気がしたんですが…。すみません、StrPtr使ってやってください(^^;;
どちらにしても、エラーにならないのはデバッグするときに無駄に時間を使わせますから、バグとして報告しておきます。
[hira]
http://hira.hopto.org/
http://hira.hopto.org/