您的位置:首页 > 其它

造了一个轮子:注册表键编辑封装->registry类

2011-01-05 16:07 246 查看
学习com组件编程时,顺便封装了一个注册表操作类,自我感觉不错,贴出来晒晒,使用方法:

先定位到一个键,然后操作 该键自身 和 该键的子键 和 该键的值。



示例:

int main()
{
	setlocale(LC_ALL, "chs");
	wstring key = L"HKEY_LOCAL_MACHINE//SOFTWARe//testkey";
	registry reg(key);
	
	if (!reg.valid()) {
		wcout << "constructor failed for:" << key << endl;
		return -1;
	}

	unsigned char buf[8] = {0x33,0x11,0x00,0x11,0x33,0x11,0x00,0x11};
	if (reg.set_value(L"字符串值", L"这是一个有set_value重载函数设置的一个字符串值") < 0)
	{
		wcout << L"reg.set_value(name, string) failed" << endl;
		return -1;
	}
	if (reg.set_value(L"双字", 3101) < 0)
	{
		wcout << L"reg.set_value(name, num) failed" << endl;
		return -1;
	}
	if (reg.set_value(L"二进制", buf, 8) < 0)
	{
		wcout << L"reg.set_value(name, bytes, size) failed " << endl;
		return -1;
	}

	unsigned long dw;
	wstring str;
	unsigned char bytes[8];
	int size = 9;

	if (reg.get_dword_value(L"双字", dw) < 0) {
		wcout << L"reg.get_dword_value 失败"<< endl;
		return -1;
	}
	wcout << L"get_dword_value" << dw << endl;

	if (reg.get_binary_value(L"二进制", bytes, size) < 0) {
		wcout << L"reg.get_binary_value 失败" << endl;
		return -1;
	}
	wcout << L"get_binary_value() size:"  << size ;
	for (int i = 0; i != size; i++)
		wcout << L" 0x" << bytes[i];
	wcout << endl;

	if (reg.get_string_value(L"字符串值", str) < 0) {
		wcout << L"reg.get_string _value 失败" << endl; 
		return -1;
	}
	wcout << L"get_string_value " << str << endl;

	reg.create_subkey(L"新键");
	registry new_reg;
	reg.get_subkey(L"新键", new_reg);

	if (!new_reg.valid()) {
		wcout << "reg.get_subkey(新键) failed" << endl;
		return -1;
	}

	new_reg.set_value(L"dword", 3103);
	unsigned long dw2;
	new_reg.get_dword_value(L"dword", dw2);
	wcout << dw2 << endl;

	new_reg.delete_value(L"dword");
	//new_reg.get_value(L"dword", 
	
	new_reg.create_subkey(L"subkey1//subkey2//subkey3");
	if (new_reg.delete_subkey(L"subkey1") < 0)
		wcout << L"delete subkey failed " << endl;
	
	return 0;
}






定义:

#ifndef REGISTRY_H
#define REGISTRY_H

#include <windows.h>
#include <shlwapi.h>
#include <string>
using std::wstring;
class registry
{
	class value
	{
	public:
		friend class registry;

		typedef enum {
			dword =			REG_DWORD, 
			string =		REG_SZ,
			binary =		REG_BINARY,
			unknown_type =	0x31013101
		} value_type_t;

		value() : type(unknown_type), length(0), data(NULL) {};
		~value(); 
		template <class num_type>
		value(const wstring &name, const num_type num)
			: type(dword)
			, name(name)
			, length(sizeof(unsigned long))
		{
			data = new unsigned char[sizeof num_type];
			*reinterpret_cast<unsigned long *>(data) = num;
		}
		value(const wstring &name, const wchar_t *str);
		value(const wstring &name, const unsigned char *bytes, int size);

		void *get_data()
		{
			if (type == dword)
				return (void *)*reinterpret_cast<unsigned long *>(data);
			return data;
		}
		
	private:
		value_type_t type;
		wstring name;
		unsigned char *data;
		int length;
	};

	// hkey + subkey  = hkey_this, hkey and subkey was needed in RegDeleteKey
	HKEY hkey;
	HKEY hkey_this;
	wstring subkey;
	void init(HKEY hkey, const wstring &key);
	int set_value(const value &value);
	int open_or_create_subkey(HKEY hkey, const wstring &subkey, HKEY &hnewkey);

public:
	registry () : hkey(NULL), hkey_this(NULL) {}
	registry(HKEY hkey, const wstring &key);
	registry(const wstring &key); // L"HKEY_LOCAL_MACHINE//Software//testkey"
	bool valid() const {return hkey != NULL && hkey_this != NULL; }

	// key interface
	int create_subkey(const wstring &subkey); // open or create
	int get_subkey(const wstring &subkey, registry ®); // no create
	int delete_subkey(const wstring &subkey = L"", bool del_tree = false); // delete self if subkey empty

	// value interface
	template <class num_type>
	int set_value(const wstring &name, num_type num);
	int set_value(const wstring &name, const wstring &str);
	int set_value(const wstring &name, const wchar_t *str);
	int set_value(const wstring &name, const unsigned char *bytes, int size);

	int get_dword_value(const wstring &name, unsigned long &v);
	int get_binary_value(const wstring &name, unsigned char *bytes, int &size);
	int get_string_value(const wstring &name, wstring &str);

	int delete_value(const wstring &name);
};
#endif




实现:

#include <iostream>
#include <locale.h>
#include "registry.h"
using namespace std;

registry::value::value(const wstring &name, const wchar_t *str)
	: type(registry::value::string)
	, name(name)
	, length(wcslen(str) * sizeof(wchar_t))
{
	data = new unsigned char [length];
	memcpy(data, str, length);
};
	
registry::value::value(const wstring &name, const unsigned char *bytes, int size)
	: type(binary)
	, name(name)
	, length(size)
{
	data = new unsigned char [length];
	memcpy(data, bytes, length);
}

registry::value::~value()
{
	type = unknown_type;
	length = 0;
	if (data)
		delete data;
	data = NULL;
}

registry::registry(HKEY hkey, const wstring &subkey)
	: hkey(NULL)
	, hkey_this(NULL)
{
	init(hkey, subkey);
}

registry::registry(const wstring &key) // L"HKEY_LOCAL_MACHINE//Software//testkey"
	: hkey(NULL)
	, hkey_this(NULL)
{
	wstring::size_type pos = key.find(L'//');
	wstring predefined_key = key.substr(0, pos);
	HKEY predefined_hkey;

	/* predefined hkeys 
		HKEY_CLASSES_ROOT 
		HKEY_CURRENT_USER 
		HKEY_LOCAL_MACHINE 
		HKEY_USERS 
		HKEY_CURRENT_CONFIG 
		HKEY_PERFORMANCE_DATA 
		HKEY_PERFORMANCE_NLSTEXT 
		HKEY_PERFORMANCE_TEXT 
	*/
	if (predefined_key == L"HKEY_CLASSES_ROOT")
		predefined_hkey = HKEY_CLASSES_ROOT;
	else if (predefined_key == L"HKEY_CURRENT_USER")
		predefined_hkey = HKEY_CURRENT_USER;
	else if (predefined_key == L"HKEY_LOCAL_MACHINE")
		predefined_hkey = HKEY_LOCAL_MACHINE;
	else if (predefined_key == L"HKEY_USERS")
		predefined_hkey = HKEY_USERS;
	else if (predefined_key == L"HKEY_CURRENT_CONFIG")
		predefined_hkey = HKEY_CURRENT_CONFIG;
	else {
		wcout << L"unsupported predefined hkey, source it in";
		throw 0;
	}
	if (pos != wstring::npos)
		pos = pos + 1;
	init(predefined_hkey, key.substr(pos));
};

int registry::open_or_create_subkey(HKEY hkey, const wstring &subkey, HKEY &hnewkey)
{
	HKEY newkey;
	unsigned long disposition;
	long ret = RegCreateKeyEx(
		hkey,
		subkey.c_str(),
		0,
		NULL,
		REG_OPTION_NON_VOLATILE,
		KEY_ALL_ACCESS,
		NULL,
		&newkey,
		&disposition
		);

	if (ret != ERROR_SUCCESS)
		return -1;

	hnewkey = newkey;
	return 0;
}
void registry::init(HKEY hkey, const wstring &subkey)
{
	HKEY thiskey;
	//long ret = RegOpenKeyEx(hkey, subkey.c_str(), 0, KEY_READ | KEY_WRITE | KEY_QUERY_VALUE, &thiskey);
	if (open_or_create_subkey(hkey, subkey, thiskey) < 0)
		return ;

	this->hkey = hkey;
	this->hkey_this = thiskey;
	this->subkey = subkey;
}

int registry::create_subkey(const wstring &subkey)
{
	HKEY newkey;
	return open_or_create_subkey(hkey_this, subkey, newkey);
}

int registry::get_subkey(const wstring &subkey, registry ®)
{
	HKEY newkey;
	long ret = RegOpenKeyEx(hkey_this, subkey.c_str(), 0, KEY_READ | KEY_WRITE | KEY_QUERY_VALUE, &newkey);
	if (ret != ERROR_SUCCESS)
		return -1;

	reg = registry(hkey_this, subkey);
	return 0;
}

int registry::delete_subkey(const wstring &subkey, bool del_tree)
{
	HKEY del_hkey;
	wstring del_subkey;
	if (subkey == L"") {
		del_hkey = hkey;
		del_subkey = this->subkey;
	} else {
		del_hkey = hkey_this;
		del_subkey = subkey;
	}

	long ret;
	if (del_tree)
#if 0
		ret = RegDeleteTreeEx(del_hkey, del_subkey.c_str());
#endif
		ret = SHDeleteKey(del_hkey, del_subkey.c_str());
	else 
		ret = RegDeleteKey(del_hkey, del_subkey.c_str());
	if (ret != ERROR_SUCCESS)
		return -1;
	return 0;
}

template <class num_type>
int registry::set_value(const wstring &name, num_type num)
{
	value v(name, num);
	return set_value(v);
}

int registry::set_value(const wstring &name, const wstring &str)
{
	return set_value(name, str.c_str());
}

int registry::set_value(const wstring &name, const wchar_t *str)
{
	value v(name, str);
	return set_value(v);
}

int registry::set_value(const wstring &name, const unsigned char *bytes, int size)
{
	value v(name, bytes, size);
	return set_value(v);
}

int registry::set_value(const value &v)
{
	if (v.type == value::unknown_type && v.length <= 0)
		return -1;
	if (RegSetValueEx(hkey_this, v.name.c_str(), 0, v.type, v.data, v.length) != ERROR_SUCCESS)
		return -1;
	return 0;
}

int registry::get_dword_value(const wstring &name, unsigned long &v)
{
	unsigned long tv, type, size = sizeof(unsigned long);
	long ret = RegQueryValueEx(hkey_this, name.c_str(), NULL, &type, (LPBYTE)&tv, &size);
	if (ret == ERROR_FILE_NOT_FOUND)
		return -3;

	if (type != REG_DWORD)
		return -2; // type mismatch

	if (ret != ERROR_SUCCESS)
		return -1;
	
	v = tv;
	return 0;
}

int registry::get_binary_value(const wstring &name, unsigned char *bytes, int &size)
{
	unsigned long type, tmp_size = size;
	if (RegQueryValueEx(hkey_this, name.c_str(),NULL, &type, bytes, &tmp_size) != ERROR_SUCCESS) 
		return -1;
	size = tmp_size;
	return 0;
}

int registry::get_string_value(const wstring &name, wstring &str)
{
	unsigned char *bytes = new unsigned char[1];
	unsigned long  type, size = 1;
	long ret;

	do {
		delete bytes;
		size *= 2;
		bytes = new unsigned char [size];
		ret = RegQueryValueEx(hkey_this, name.c_str(), NULL, &type, bytes, &size);
	} while (ret == ERROR_MORE_DATA);

	if (ret != ERROR_SUCCESS)
		return -1;

	str = wstring(reinterpret_cast<wchar_t *>(bytes));
	delete bytes;
	return 0;
}

int registry::delete_value(const wstring &name)
{
	return RegDeleteValue(hkey_this, name.c_str()) == ERROR_SUCCESS ? 0 : -1;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐