登錄檔中RegSetValueEx用法
阿新 • • 發佈:2019-01-07
如今修改登錄檔成為繼超頻之後的又一大熱點,許多CFAN通過對登錄檔的修改使Win98顯得更加個性化,諸多報刊雜誌也紛紛扯起登錄檔這面旗幟,令人遺憾的是,在介紹登錄檔修改的眾多的文章中,大都以手工修改為例,極少數文章也只介紹有關修改登錄檔軟體的用法,至於如何在程式中實現卻無人提及。為此我在Visual Studio6.0幫助檔案中用Registry關鍵字進行搜尋,在翻譯軟體幫助下及不斷的上機實踐下,我終於摸索出使用登錄檔介面(API)函式的一些用法,現拿出來與大家共享。
在程式中使用登錄檔,不外乎建立、開啟、讀取、設定、刪除這五個常規操作,(要想獲得更詳細的資料可以參考Visual Studio6.0幫助目錄中MSDN Library Visual Studio6.0|Platform SDK|Window Base Services|General Library|Registry條目)。下面我們就來關注這五個介面函式的用法:
一、 建立鍵RegCreateKeyEx
通過RegCreateKeyEx函式可以在登錄檔中建立鍵,如果需要建立的鍵已經存在了,則開啟鍵。函式原型如下:
LONG RegCreateKeyEx(
HKEY hKey,
LPCTSTR lpSubKey,
DWORD Reserved,
LPTSTR lpClass,
DWORD dwOptions,
REGSAM samDesired,
LPSECURITY_ATTRIBUTESlpSecurityAttributes,
PHKEY phkResult,
LPDWORD lpdwDisposition
);
各引數及返回值的含義如下:
?hKey為主鍵值,可以取下面的一些數值:
HKEY_CLASSES_ROOT、HKEY_CURRENT_CONFIG
HKEY_CURRENT_USER、HKEY_LOCAL_MACHINE
HKEY_USER、HKEY_PERFORMANCE_DATA(WINNT作業系統)
HKEY_DYN_DATA(WIN9X作業系統)
?引數lpSubKey為一個指向以零結尾的字串的指標,其中包含將要建立或開啟的子鍵的名稱。子鍵不可以用反斜線()開始。該引數可以為NULL。
?Reserved保留,必須設定為0。
?引數lpClass一個指向包含鍵型別的字串。如果該鍵已經存在,則忽略該引數。
?引數dwOptions為新建立的鍵設定一定的屬性。可以取下面的一些數值:
REG_OPTION_NON_VOLATILE 新建立的鍵為一個非短暫性的鍵(資料資訊儲存在檔案中,當系統重新啟動時,資料資訊恢復)
REG_OPTION_VOLATILE 新建立的鍵為一個短暫性的鍵(資料資訊儲存在記憶體中)。Windows95忽略該數值。
REG_OPTION_BACKUP_RESTORE 僅在WINNT中支援,可以提供優先順序支援。
?引數samDesired用來設定對鍵訪問的許可權,可以取下面的一些數值:
KEY_CREATE_LINK 准許生成符號鍵
KEY_CREATE_SUB_KEY 准許生成子鍵
KEY_ENUMERATE_SUB_KEYS 准許生成列舉子鍵
KEY_EXECUTE 准許進行讀操作
KEY_NOTIFY 准許更換通告
KEY_QUERY_VALUE 准許查詢子鍵
KEY_ALL_ACCESS 提供完全訪問,是上面數值的組合
KEY_READ 是下面數值的組合:
KEY_QUERY_VALUE、KEY_ENUMERATE_SUB_KEYS、KEY_NOTIFY
KEY_SET_VALUE 准許設定子鍵的數值
KEY_WRITE 是下面數值的組合:
KEY_SET_VALUE、KEY_CREATE_SUB_KEY
?引數lpSecurityAttributes為一個指向SECURITY_ATTRIBUTES結構的指標,確定返回的控制代碼是否被子處理過程繼承。如果該引數為NULL,則控制代碼不可以被繼承。在WINNT中,該引數可以為新建立的鍵增加安全的描述。
?引數phkResult為一個指向新建立或開啟的鍵的控制代碼的指標。
?引數lpdwDispition指明鍵是被建立還是被開啟的,可以是下面的一些數值:
REG_CREATE_NEW_KEY 鍵先前不存在,現在被建立。
REG_OPENED_EXISTING_KEY 鍵先前已存在,現在被開啟。
?返回值 如果函式呼叫成功,則返回ERROR_SUCCESS。否則,返回值為檔案WINERROR.h中定義的一個非零的錯誤程式碼,可以通過設定FORMAT_MESSAGE_FROM_SYSTEM標識呼叫FormatMessage函式來獲取一個對錯誤的總體描述。
二、 開啟一個鍵RegOpenKeyEx
RegOpenKeyEx函式可以開啟一個指定的鍵,函式原型如下:
LONG RegOpenKeyEx(
HKEY hkey,
LPCTSTR lpSubKey,
DWORD ulOption,
REGSAM samDesired,
PHKEY phkResult
);
各引數及返回值的含義如下:
?引數hKey的含義同RegCreateKeyEx函式中的hKey引數。
?引數lpSubKey為一個指向以零結尾的字串的指標,其中包含子鍵的名稱,可以利用反斜線()分隔不同的子鍵名。如果字串為空,則根據hKey引數建立一個新的控制代碼。在這種情況下,並不關閉先前開啟的控制代碼。
?ulOption保留,通常必須設定為0。
?引數samDesired的含義同RegCreateKeyEx函式中的samDesired引數。
?引數phkResult為一個指標,用來指向開啟的鍵的控制代碼。可以通過RegCloseKey函式關閉這個控制代碼。
?返回值同RegCreateKeyEx函式的返回值。
三、 讀取鍵RegQueryValueEx
通過RegQueryValueEx函式可以從一個已經開啟的鍵中讀取資料,函式原型如下:
LONG RegQueryValueEx(
HKEY hKey,
LPTSTR lpValueName,
LPDWORD lpReserved,
LPDWORD lpType,
LPBYTE lpData,
LPDWORD lpcbData
);
各個引數及返回值的含義如下:
?引數hKey為當前的一個開啟的鍵的控制代碼,具體數值同RegCreateKeyEx函式的hKey引數。
?引數lpVauleName為一個指向非空的包含查詢值的名稱的字串指標。
?lpReserved保留,必須為NULL。
?引數lpType為一個指向資料型別的指標,資料型別為下列型別之一:
REG_BINARY 二進位制資料
REG_DWORD 32位整數
REG_DWORD_LITTLE_ENDIAN little-endian格式的資料,例如0X12345678以(0X78 0X56 0X34 0X12)方式儲存
REG_DWORD_BIG_ENDIAN big-endian格式的資料,例如0X12345678以(0X12 0X34 0X56 0X78)方式儲存
REG_EXPAND_SZ 一個包含未擴充套件環境變數的字串
REG_LINK 一個Unicode型別的連結
REG_MULIT_SZ 以兩個零結尾的字串
REG_NONE 無型別數值
REG_RESOURCE_LIST 裝置驅動資源列表
REG_SZ 一個以零結尾的字串根據函式使用的字符集型別的不同而設定為Unicode或ANSI型別的字串
?引數lpData為一個指向儲存返回值的變數的指標。如果不需要返回值,該引數可以為NULL。
?引數lpcbData為一個指向儲存返回值長度的變數的指標。其中長度以位元組為單位。如果資料型別為REG_SZ、REG_MULTI_SZ或REG_EXPAND_SZ,那麼長度也包括結尾的零字元,只有在引數lpData為NULL時,引數lpcbData才可以為NULL。
?返回值同RegCreateKeyEx函式的返回值。
四、 設定鍵值RegSetValueEx
RegSetValueEx函式可以設定登錄檔中鍵的值,函式原型如下:
LONG RegSetValueEx(
HKEY hKey,
LPCTSTR lpValueName,
DWORD Reserved,
DWORD dwType,
CONST BYTE *lpData,
DWORD cbData
);
各個引數及返回值的含義如下:
?引數hKey的含義同RegCreateKeyEx函式中的hKey引數。
?引數lpValueName為一個指向包含值名的字串指標。
?Reserved保留,通常必須設定為0。
?引數dwType確定了設定的值的型別同RegQueryValueKeyEx的lyType引數。
?引數lpData為一個指向包含資料的緩衝區的指標。
?引數cbData以位元組為單位,指定資料的長度。
?返回值同RegCreateKeyEx函式的返回值。
五、 刪除鍵值RegDeketeKey
函式RegDeketeKey刪除一個鍵及所有的子鍵。函式原型如下:
LONG RegDeleteKey(
HKEY hKey,
LPCTSTR lpSubKEY
);
各個引數及返回值的含義如下:
?引數hKey的含義同RegCreateKeyEx函式中的hKey引數。
?引數lpSubKey的含義同RegCreateKeyEx函式中的lpSubKey引數。
六、 示例
下面我們在Visual C++6.0或5.0環境中新建一基於對話方塊的工程。設定兩個命令按鈕,名為“查詢使用者資訊”和“修改使用者資訊”,用來查詢和修改登錄檔中的使用者姓名和公司名稱。需要說明的是,使用者的資訊位於系統登錄檔中KEY-CURRENT-USERSoftwareMicrsoftMS Setup(ACME)User Info的位置,鍵值名DefName和DefCompany分別表示使用者的姓名和使用者公司的名稱。
1、 查詢使用者資訊的程式碼
HKEY hKey; //定義有關的hKey,在查詢結束時要關閉。
LPCTSTR path="Software/Micrsoft/MS Setup(ACME)/User Info/”;
LONG return0=(::RegOpenKeyEx(HKEY_CURRENT_USER,path,0,KEY_READ,&hKey));
if(return0!=ERROR_SUCCESS)
{
MessageBox("錯誤:無法開啟有關的鍵!");
Return;
}
LPBYTE username_Get=new BYTE[80];
DWORD type_1=REG_SZ;
DWORD cbData_1=80;
LONG return1=::RegQueryValueEx(hKey,"Defname:,NULL,&type_1,
username_Get,&cbData_1);
if(return1!=ERROR_SUCCESS)
{
MessageBox("錯誤:無法查詢有關注冊表資訊!");
Return;
}
LPBYTE company_Get=new BYTE[80];
DWORD type_2=REG_SZ;
DWORD cbData_2=80;
LONG return2=::RegQueryValueEx(hKey,"DefCompany",NULL,&type_2,
company_Get,&cbData_2);
if(return2!=ERROR_SUCCESS)
{
MessageBox("錯誤:無法查詢有關注冊表資訊!");
Return;
}
//將username_Get和company_Get轉換為CString字串,以便顯示輸出
CString str_username=CString(username_Get);
CString str_company=CString(company_Get);
delete[] username_Get;
delete[] company_Get;
//程式結束前關閉已經開啟的hKey
::RegCloseKey(hKey);
……
字串str_username和str_company表示查詢的使用者的姓名和公司的名稱。
2、修改使用者資訊的程式碼
因使用者輸出的是CString型別的字串,要先將其轉換為LPBYTE型別,以便以後函式的呼叫。下面是轉換函式:
LPBYTE CString_To_LPBYTE(CString str)
{
LPBYTE lpb=new BYTE [str.GetLength( )+1];
for(int i=0;i<STR. GetLength( );i++)lpb[i]="str[i];
lpb[str.GetLength( )]=0;
return lpb;
}
以下是具體的修改登錄檔使用者資訊的程式碼:
CString str_username,str_company;
HKEY hKey;
LPCTSTR path=“Software/Micrsoft/MS Setup(ACME)/User Info/”;
LONG return0(::RegOpenKeyEx(HKEY_CURRENT_USER,path,0,KEY_WRITE,&hKey));
if(return0!=ERROR_SUCCESS)
{
MessageBox(“錯誤:無法開啟有關的鍵!”);
return;
}
LPBYTE username_Set=Cstring_To_LPBYTE(str_username);
DWORD type_1=REG_SZ;
DWORD cbData_1=str_username.GetLength( )+1;
LONG return1=::RegSetalueEx(hKey," DefName?,NULL,type_1,username_Set,cbData_1);
if (return1!=ERROR_SUCCESS)
{
MessageBox(“錯誤:無法修改有關注冊表資訊!”);
return;
}
LPBYTE company_Set=Cstring_To_LPBYTE(str_company);
DWORD type_2=REG_SZ;
DWORD cbData_2=str_COMPANY.GetLength( )+1;
LONG return2=::RegSetalueEx(hKey,"DefCompany",NULL,type_2,company_Set,cbData_2);
if (return2!=ERROR_SUCCESS)
{
MessageBox(“錯誤:無法修改有關注冊表資訊!”);
return;
}
在程式中使用登錄檔,不外乎建立、開啟、讀取、設定、刪除這五個常規操作,(要想獲得更詳細的資料可以參考Visual Studio6.0幫助目錄中MSDN Library Visual Studio6.0|Platform SDK|Window Base Services|General Library|Registry條目)。下面我們就來關注這五個介面函式的用法:
一、 建立鍵RegCreateKeyEx
通過RegCreateKeyEx函式可以在登錄檔中建立鍵,如果需要建立的鍵已經存在了,則開啟鍵。函式原型如下:
LONG RegCreateKeyEx(
HKEY hKey,
LPCTSTR lpSubKey,
DWORD Reserved,
LPTSTR lpClass,
DWORD dwOptions,
REGSAM samDesired,
LPSECURITY_ATTRIBUTESlpSecurityAttributes,
PHKEY phkResult,
LPDWORD lpdwDisposition
);
各引數及返回值的含義如下:
?hKey為主鍵值,可以取下面的一些數值:
HKEY_CLASSES_ROOT、HKEY_CURRENT_CONFIG
HKEY_CURRENT_USER、HKEY_LOCAL_MACHINE
HKEY_USER、HKEY_PERFORMANCE_DATA(WINNT作業系統)
HKEY_DYN_DATA(WIN9X作業系統)
?引數lpSubKey為一個指向以零結尾的字串的指標,其中包含將要建立或開啟的子鍵的名稱。子鍵不可以用反斜線()開始。該引數可以為NULL。
?Reserved保留,必須設定為0。
?引數lpClass一個指向包含鍵型別的字串。如果該鍵已經存在,則忽略該引數。
?引數dwOptions為新建立的鍵設定一定的屬性。可以取下面的一些數值:
REG_OPTION_NON_VOLATILE 新建立的鍵為一個非短暫性的鍵(資料資訊儲存在檔案中,當系統重新啟動時,資料資訊恢復)
REG_OPTION_VOLATILE 新建立的鍵為一個短暫性的鍵(資料資訊儲存在記憶體中)。Windows95忽略該數值。
REG_OPTION_BACKUP_RESTORE 僅在WINNT中支援,可以提供優先順序支援。
?引數samDesired用來設定對鍵訪問的許可權,可以取下面的一些數值:
KEY_CREATE_LINK 准許生成符號鍵
KEY_CREATE_SUB_KEY 准許生成子鍵
KEY_ENUMERATE_SUB_KEYS 准許生成列舉子鍵
KEY_EXECUTE 准許進行讀操作
KEY_NOTIFY 准許更換通告
KEY_QUERY_VALUE 准許查詢子鍵
KEY_ALL_ACCESS 提供完全訪問,是上面數值的組合
KEY_READ 是下面數值的組合:
KEY_QUERY_VALUE、KEY_ENUMERATE_SUB_KEYS、KEY_NOTIFY
KEY_SET_VALUE 准許設定子鍵的數值
KEY_WRITE 是下面數值的組合:
KEY_SET_VALUE、KEY_CREATE_SUB_KEY
?引數lpSecurityAttributes為一個指向SECURITY_ATTRIBUTES結構的指標,確定返回的控制代碼是否被子處理過程繼承。如果該引數為NULL,則控制代碼不可以被繼承。在WINNT中,該引數可以為新建立的鍵增加安全的描述。
?引數phkResult為一個指向新建立或開啟的鍵的控制代碼的指標。
?引數lpdwDispition指明鍵是被建立還是被開啟的,可以是下面的一些數值:
REG_CREATE_NEW_KEY 鍵先前不存在,現在被建立。
REG_OPENED_EXISTING_KEY 鍵先前已存在,現在被開啟。
?返回值 如果函式呼叫成功,則返回ERROR_SUCCESS。否則,返回值為檔案WINERROR.h中定義的一個非零的錯誤程式碼,可以通過設定FORMAT_MESSAGE_FROM_SYSTEM標識呼叫FormatMessage函式來獲取一個對錯誤的總體描述。
二、 開啟一個鍵RegOpenKeyEx
RegOpenKeyEx函式可以開啟一個指定的鍵,函式原型如下:
LONG RegOpenKeyEx(
HKEY hkey,
LPCTSTR lpSubKey,
DWORD ulOption,
REGSAM samDesired,
PHKEY phkResult
);
各引數及返回值的含義如下:
?引數hKey的含義同RegCreateKeyEx函式中的hKey引數。
?引數lpSubKey為一個指向以零結尾的字串的指標,其中包含子鍵的名稱,可以利用反斜線()分隔不同的子鍵名。如果字串為空,則根據hKey引數建立一個新的控制代碼。在這種情況下,並不關閉先前開啟的控制代碼。
?ulOption保留,通常必須設定為0。
?引數samDesired的含義同RegCreateKeyEx函式中的samDesired引數。
?引數phkResult為一個指標,用來指向開啟的鍵的控制代碼。可以通過RegCloseKey函式關閉這個控制代碼。
?返回值同RegCreateKeyEx函式的返回值。
三、 讀取鍵RegQueryValueEx
通過RegQueryValueEx函式可以從一個已經開啟的鍵中讀取資料,函式原型如下:
LONG RegQueryValueEx(
HKEY hKey,
LPTSTR lpValueName,
LPDWORD lpReserved,
LPDWORD lpType,
LPBYTE lpData,
LPDWORD lpcbData
);
各個引數及返回值的含義如下:
?引數hKey為當前的一個開啟的鍵的控制代碼,具體數值同RegCreateKeyEx函式的hKey引數。
?引數lpVauleName為一個指向非空的包含查詢值的名稱的字串指標。
?lpReserved保留,必須為NULL。
?引數lpType為一個指向資料型別的指標,資料型別為下列型別之一:
REG_BINARY 二進位制資料
REG_DWORD 32位整數
REG_DWORD_LITTLE_ENDIAN little-endian格式的資料,例如0X12345678以(0X78 0X56 0X34 0X12)方式儲存
REG_DWORD_BIG_ENDIAN big-endian格式的資料,例如0X12345678以(0X12 0X34 0X56 0X78)方式儲存
REG_EXPAND_SZ 一個包含未擴充套件環境變數的字串
REG_LINK 一個Unicode型別的連結
REG_MULIT_SZ 以兩個零結尾的字串
REG_NONE 無型別數值
REG_RESOURCE_LIST 裝置驅動資源列表
REG_SZ 一個以零結尾的字串根據函式使用的字符集型別的不同而設定為Unicode或ANSI型別的字串
?引數lpData為一個指向儲存返回值的變數的指標。如果不需要返回值,該引數可以為NULL。
?引數lpcbData為一個指向儲存返回值長度的變數的指標。其中長度以位元組為單位。如果資料型別為REG_SZ、REG_MULTI_SZ或REG_EXPAND_SZ,那麼長度也包括結尾的零字元,只有在引數lpData為NULL時,引數lpcbData才可以為NULL。
?返回值同RegCreateKeyEx函式的返回值。
四、 設定鍵值RegSetValueEx
RegSetValueEx函式可以設定登錄檔中鍵的值,函式原型如下:
LONG RegSetValueEx(
HKEY hKey,
LPCTSTR lpValueName,
DWORD Reserved,
DWORD dwType,
CONST BYTE *lpData,
DWORD cbData
);
各個引數及返回值的含義如下:
?引數hKey的含義同RegCreateKeyEx函式中的hKey引數。
?引數lpValueName為一個指向包含值名的字串指標。
?Reserved保留,通常必須設定為0。
?引數dwType確定了設定的值的型別同RegQueryValueKeyEx的lyType引數。
?引數lpData為一個指向包含資料的緩衝區的指標。
?引數cbData以位元組為單位,指定資料的長度。
?返回值同RegCreateKeyEx函式的返回值。
五、 刪除鍵值RegDeketeKey
函式RegDeketeKey刪除一個鍵及所有的子鍵。函式原型如下:
LONG RegDeleteKey(
HKEY hKey,
LPCTSTR lpSubKEY
);
各個引數及返回值的含義如下:
?引數hKey的含義同RegCreateKeyEx函式中的hKey引數。
?引數lpSubKey的含義同RegCreateKeyEx函式中的lpSubKey引數。
六、 示例
下面我們在Visual C++6.0或5.0環境中新建一基於對話方塊的工程。設定兩個命令按鈕,名為“查詢使用者資訊”和“修改使用者資訊”,用來查詢和修改登錄檔中的使用者姓名和公司名稱。需要說明的是,使用者的資訊位於系統登錄檔中KEY-CURRENT-USERSoftwareMicrsoftMS Setup(ACME)User Info的位置,鍵值名DefName和DefCompany分別表示使用者的姓名和使用者公司的名稱。
1、 查詢使用者資訊的程式碼
HKEY hKey; //定義有關的hKey,在查詢結束時要關閉。
LPCTSTR path="Software/Micrsoft/MS Setup(ACME)/User Info/”;
LONG return0=(::RegOpenKeyEx(HKEY_CURRENT_USER,path,0,KEY_READ,&hKey));
if(return0!=ERROR_SUCCESS)
{
MessageBox("錯誤:無法開啟有關的鍵!");
Return;
}
LPBYTE username_Get=new BYTE[80];
DWORD type_1=REG_SZ;
DWORD cbData_1=80;
LONG return1=::RegQueryValueEx(hKey,"Defname:,NULL,&type_1,
username_Get,&cbData_1);
if(return1!=ERROR_SUCCESS)
{
MessageBox("錯誤:無法查詢有關注冊表資訊!");
Return;
}
LPBYTE company_Get=new BYTE[80];
DWORD type_2=REG_SZ;
DWORD cbData_2=80;
LONG return2=::RegQueryValueEx(hKey,"DefCompany",NULL,&type_2,
company_Get,&cbData_2);
if(return2!=ERROR_SUCCESS)
{
MessageBox("錯誤:無法查詢有關注冊表資訊!");
Return;
}
//將username_Get和company_Get轉換為CString字串,以便顯示輸出
CString str_username=CString(username_Get);
CString str_company=CString(company_Get);
delete[] username_Get;
delete[] company_Get;
//程式結束前關閉已經開啟的hKey
::RegCloseKey(hKey);
……
字串str_username和str_company表示查詢的使用者的姓名和公司的名稱。
2、修改使用者資訊的程式碼
因使用者輸出的是CString型別的字串,要先將其轉換為LPBYTE型別,以便以後函式的呼叫。下面是轉換函式:
LPBYTE CString_To_LPBYTE(CString str)
{
LPBYTE lpb=new BYTE [str.GetLength( )+1];
for(int i=0;i<STR. GetLength( );i++)lpb[i]="str[i];
lpb[str.GetLength( )]=0;
return lpb;
}
以下是具體的修改登錄檔使用者資訊的程式碼:
CString str_username,str_company;
HKEY hKey;
LPCTSTR path=“Software/Micrsoft/MS Setup(ACME)/User Info/”;
LONG return0(::RegOpenKeyEx(HKEY_CURRENT_USER,path,0,KEY_WRITE,&hKey));
if(return0!=ERROR_SUCCESS)
{
MessageBox(“錯誤:無法開啟有關的鍵!”);
return;
}
LPBYTE username_Set=Cstring_To_LPBYTE(str_username);
DWORD type_1=REG_SZ;
DWORD cbData_1=str_username.GetLength( )+1;
LONG return1=::RegSetalueEx(hKey," DefName?,NULL,type_1,username_Set,cbData_1);
if (return1!=ERROR_SUCCESS)
{
MessageBox(“錯誤:無法修改有關注冊表資訊!”);
return;
}
LPBYTE company_Set=Cstring_To_LPBYTE(str_company);
DWORD type_2=REG_SZ;
DWORD cbData_2=str_COMPANY.GetLength( )+1;
LONG return2=::RegSetalueEx(hKey,"DefCompany",NULL,type_2,company_Set,cbData_2);
if (return2!=ERROR_SUCCESS)
{
MessageBox(“錯誤:無法修改有關注冊表資訊!”);
return;
}