java 注册表_Java Windows下读取注册表的工具类

这是一个Java工具类,用于在Windows环境下读取注册表。提供了多种方法,如根据路径获取键值、获取路径下所有数据、递归获取键值等。类中使用反射调用Preferences类的私有方法来实现注册表操作。示例代码展示了如何使用该工具类查询Windows系统中已安装软件的名称。
摘要由CSDN通过智能技术生成

importjava.io.BufferedReader;importjava.io.IOException;importjava.io.InputStreamReader;importjava.lang.reflect.InvocationTargetException;importjava.lang.reflect.Method;importjava.util.HashMap;importjava.util.Map;importjava.util.ArrayList;importjava.util.List;importjava.util.StringTokenizer;importjava.util.prefs.Preferences;/*** Windows下读取注册表的工具类

*

* 使用这些方法的示例如下:

*

* 下面的方法从给定路径检索键的值:

*

* String hex = WinRegistry.valueForKey(WinRegistry.HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\WindowsUpdate\\Auto Update", "AUOptions");

*

* 此方法检索指定路径的所有数据(以键和值的形式):

*

* Map map = WinRegistry.valuesForPath(WinRegistry.HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\WSMAN");

*

* 此方法从给定路径递归检索键的值:

*

* String val = WinRegistry.valueForKeyPath(WinRegistry.HKEY_LOCAL_MACHINE, "System", "TypeID");

*

* 并且这个方法递归地从给定路径中检索一个键的所有值:

*

* List list = WinRegistry.valuesForKeyPath( WinRegistry.HKEY_LOCAL_MACHINE, //HKEY "SOFTWARE\\Wow6432Node\\Microsoft\\Windows\\CurrentVersion\\Uninstall", //path "DisplayName" //Key );

*

* 在上面的代码中,我检索了Windows系统中所有已安装的软件名称。

*

* 注意:请参阅这些方法的文档。

*

* 这个检索给定路径的所有子键:

*

* List list3 = WinRegistry.subKeysForPath(WinRegistry.HKEY_CURRENT_USER, "Software");

*

* 注意:在这个过程中,我只修改了阅读目的的方法,而不是像createKey、删除Key等写作目的的方法。它们仍然和我收到的一样。

*

*https://cloud.tencent.com/developer/ask/43600

*/@SuppressWarnings("all")public classWinRegistry {private static final int REG_SUCCESS = 0;private static final int REG_NOTFOUND = 2;private static final int KEY_READ = 0x20019;private static final int REG_ACCESSDENIED = 5;private static final int KEY_ALL_ACCESS = 0xf003f;public static final int HKEY_CLASSES_ROOT = 0x80000000;public static final int HKEY_CURRENT_USER = 0x80000001;public static final int HKEY_LOCAL_MACHINE = 0x80000002;private static final String CLASSES_ROOT = "HKEY_CLASSES_ROOT";private static final String CURRENT_USER = "HKEY_CURRENT_USER";private static final String LOCAL_MACHINE = "HKEY_LOCAL_MACHINE";private static Preferences userRoot =Preferences.userRoot();private static Preferences systemRoot =Preferences.systemRoot();private static Class extends Preferences> userClass =userRoot.getClass();private static Method regOpenKey = null;private static Method regCloseKey = null;private static Method regQueryValueEx = null;private static Method regEnumValue = null;private static Method regQueryInfoKey = null;private static Method regEnumKeyEx = null;private static Method regCreateKeyEx = null;private static Method regSetValueEx = null;private static Method regDeleteKey = null;private static Method regDeleteValue = null;static{try{

regOpenKey= userClass.getDeclaredMethod("WindowsRegOpenKey", new Class[] {int.class, byte[].class, int.class});

regOpenKey.setAccessible(true);

regCloseKey= userClass.getDeclaredMethod("WindowsRegCloseKey", new Class[] {int.class});

regCloseKey.setAccessible(true);

regQueryValueEx= userClass.getDeclaredMethod("WindowsRegQueryValueEx", new Class[] {int.class, byte[].class});

regQueryValueEx.setAccessible(true);

regEnumValue= userClass.getDeclaredMethod("WindowsRegEnumValue", new Class[] {int.class, int.class, int.class});

regEnumValue.setAccessible(true);

regQueryInfoKey= userClass.getDeclaredMethod("WindowsRegQueryInfoKey1", new Class[] {int.class});

regQueryInfoKey.setAccessible(true);

regEnumKeyEx= userClass.getDeclaredMethod("WindowsRegEnumKeyEx", new Class[] {int.class, int.class, int.class});

regEnumKeyEx.setAccessible(true);

regCreateKeyEx= userClass.getDeclaredMethod("WindowsRegCreateKeyEx", new Class[] {int.class, byte[].class});

regCreateKeyEx.setAccessible(true);

regSetValueEx= userClass.getDeclaredMethod("WindowsRegSetValueEx", new Class[] {int.class, byte[].class, byte[].class});

regSetValueEx.setAccessible(true);

regDeleteValue= userClass.getDeclaredMethod("WindowsRegDeleteValue", new Class[] {int.class, byte[].class});

regDeleteValue.setAccessible(true);

regDeleteKey= userClass.getDeclaredMethod("WindowsRegDeleteKey", new Class[] {int.class, byte[].class});

regDeleteKey.setAccessible(true);

}catch(Exception e) {

e.printStackTrace();

}

}/*** Reads value for the key from given path

*@paramhkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE

*@parampath

*@paramkey

*@returnthe value

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException

*@throwsIOException*/

public static String valueForKey(inthkey, String path, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {if (hkey ==HKEY_LOCAL_MACHINE)returnvalueForKey(systemRoot, hkey, path, key);else if (hkey ==HKEY_CURRENT_USER)returnvalueForKey(userRoot, hkey, path, key);else

return valueForKey(null, hkey, path, key);

}/*** Reads all key(s) and value(s) from given path

*@paramhkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE

*@parampath

*@returnthe map of key(s) and corresponding value(s)

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException

*@throwsIOException*/

public static Map valuesForPath(inthkey, String path)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {if (hkey ==HKEY_LOCAL_MACHINE)returnvaluesForPath(systemRoot, hkey, path);else if (hkey ==HKEY_CURRENT_USER)returnvaluesForPath(userRoot, hkey, path);else

return valuesForPath(null, hkey, path);

}/*** Read all the subkey(s) from a given path

*@paramhkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE

*@parampath

*@returnthe subkey(s) list

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException*/

public static List subKeysForPath(inthkey, String path)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {if (hkey ==HKEY_LOCAL_MACHINE)returnsubKeysForPath(systemRoot, hkey, path);else if (hkey ==HKEY_CURRENT_USER)returnsubKeysForPath(userRoot, hkey, path);else

return subKeysForPath(null, hkey, path);

}/*** Create a key

*@paramhkey HKEY_CURRENT_USER/HKEY_LOCAL_MACHINE

*@paramkey

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException*/

public static void createKey(inthkey, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {int[] ret;if (hkey ==HKEY_LOCAL_MACHINE) {

ret=createKey(systemRoot, hkey, key);

regCloseKey.invoke(systemRoot,new Object[] { new Integer(ret[0]) });

}else if (hkey ==HKEY_CURRENT_USER) {

ret=createKey(userRoot, hkey, key);

regCloseKey.invoke(userRoot,new Object[] { new Integer(ret[0]) });

}else

throw new IllegalArgumentException("hkey=" +hkey);if (ret[1] !=REG_SUCCESS)throw new IllegalArgumentException("rc=" + ret[1] + " key=" +key);

}/*** Write a value in a given key/value name

*@paramhkey

*@paramkey

*@paramvalueName

*@paramvalue

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException*/

public static void writeStringValue(inthkey, String key, String valueName, String value)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {if (hkey ==HKEY_LOCAL_MACHINE)

writeStringValue(systemRoot, hkey, key, valueName, value);else if (hkey ==HKEY_CURRENT_USER)

writeStringValue(userRoot, hkey, key, valueName, value);else

throw new IllegalArgumentException("hkey=" +hkey);

}/*** Delete a given key

*@paramhkey

*@paramkey

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException*/

public static void deleteKey(inthkey, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {int rc = -1;if (hkey ==HKEY_LOCAL_MACHINE)

rc=deleteKey(systemRoot, hkey, key);else if (hkey ==HKEY_CURRENT_USER)

rc=deleteKey(userRoot, hkey, key);if (rc !=REG_SUCCESS)throw new IllegalArgumentException("rc=" + rc + " key=" +key);

}/*** delete a value from a given key/value name

*@paramhkey

*@paramkey

*@paramvalue

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException*/

public static void deleteValue(inthkey, String key, String value)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {int rc = -1;if (hkey ==HKEY_LOCAL_MACHINE)

rc=deleteValue(systemRoot, hkey, key, value);else if (hkey ==HKEY_CURRENT_USER)

rc=deleteValue(userRoot, hkey, key, value);if (rc !=REG_SUCCESS)throw new IllegalArgumentException("rc=" + rc + " key=" + key + " value=" +value);

}//=====================

private static int deleteValue(Preferences root, inthkey, String key, String value)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {new Integer(hkey), toCstr(key), newInteger(KEY_ALL_ACCESS)});if (handles[1] !=REG_SUCCESS)return handles[1]; //can be REG_NOTFOUND, REG_ACCESSDENIED

int rc =((Integer) regDeleteValue.invoke(root, new Object[] {new Integer(handles[0]), toCstr(value)})).intValue();

regCloseKey.invoke(root,new Object[] { new Integer(handles[0])});returnrc;

}private static int deleteKey(Preferences root, inthkey, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {int rc =((Integer) regDeleteKey.invoke(root, new Object[] {newInteger(hkey), toCstr(key)})).intValue();return rc; //can REG_NOTFOUND, REG_ACCESSDENIED, REG_SUCCESS

}private static String valueForKey(Preferences root, inthkey, String path, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {new Integer(hkey), toCstr(path), newInteger(KEY_READ)});if (handles[1] !=REG_SUCCESS)throw new IllegalArgumentException("The system can not find the specified path: '"+getParentKey(hkey)+"\\"+path+"'");byte[] valb = (byte[]) regQueryValueEx.invoke(root, new Object[] {new Integer(handles[0]), toCstr(key)});

regCloseKey.invoke(root,new Object[] {new Integer(handles[0])});return (valb != null ?parseValue(valb) : queryValueForKey(hkey, path, key));

}private static String queryValueForKey(int hkey, String path, String key) throwsIOException {returnqueryValuesForPath(hkey, path).get(key);

}private static Map valuesForPath(Preferences root, inthkey, String path)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {

HashMap results = new HashMap();int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {new Integer(hkey), toCstr(path), newInteger(KEY_READ)});if (handles[1] !=REG_SUCCESS)throw new IllegalArgumentException("The system can not find the specified path: '"+getParentKey(hkey)+"\\"+path+"'");int[] info = (int[]) regQueryInfoKey.invoke(root, new Object[] {new Integer(handles[0])});int count = info[2]; //Fixed: info[0] was being used here

int maxlen = info[4]; //while info[3] was being used here, causing wrong results

for(int index=0; index

String vald=parseValue(valb);if(valb == null ||vald.isEmpty())returnqueryValuesForPath(hkey, path);

results.put(vald, valueForKey(root, hkey, path, vald));

}

regCloseKey.invoke(root,new Object[] {new Integer(handles[0])});returnresults;

}/*** Searches recursively into the path to find the value for key. This method gives

* only first occurrence value of the key. If required to get all values in the path

* recursively for this key, then {@link#valuesForKeyPath(int hkey, String path, String key)}

* should be used.

*@paramhkey

*@parampath

*@paramkey

*@paramlist

*@returnthe value of given key obtained recursively

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException

*@throwsIOException*/

public static String valueForKeyPath(inthkey, String path, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {

String val;try{

val= valuesForKeyPath(hkey, path, key).get(0);

}catch(IndexOutOfBoundsException e) {throw new IllegalArgumentException("The system can not find the key: '"+key+"' after "

+ "searching the specified path: '"+getParentKey(hkey)+"\\"+path+"'");

}returnval;

}/*** Searches recursively into given path for particular key and stores obtained value in list

*@paramhkey

*@parampath

*@paramkey

*@paramlist

*@returnlist containing values for given key obtained recursively

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException

*@throwsIOException*/

public static List valuesForKeyPath(inthkey, String path, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {

List list = new ArrayList();if (hkey ==HKEY_LOCAL_MACHINE)returnvaluesForKeyPath(systemRoot, hkey, path, key, list);else if (hkey ==HKEY_CURRENT_USER)returnvaluesForKeyPath(userRoot, hkey, path, key, list);else

return valuesForKeyPath(null, hkey, path, key, list);

}private static List valuesForKeyPath(Preferences root, int hkey, String path, String key, Listlist)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {if(!isDirectory(root, hkey, path)) {

takeValueInListForKey(hkey, path, key, list);

}else{

List subKeys =subKeysForPath(root, hkey, path);for(String subkey: subKeys) {

String newPath= path+"\\"+subkey;if(isDirectory(root, hkey, newPath))

valuesForKeyPath(root, hkey, newPath, key, list);

takeValueInListForKey(hkey, newPath, key, list);

}

}returnlist;

}/*** Takes value for key in list

*@paramhkey

*@parampath

*@paramkey

*@paramlist

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException

*@throwsIOException*/

private static void takeValueInListForKey(int hkey, String path, String key, Listlist)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException, IOException {

String value=valueForKey(hkey, path, key);if(value != null)

list.add(value);

}/*** Checks if the path has more subkeys or not

*@paramroot

*@paramhkey

*@parampath

*@returntrue if path has subkeys otherwise false

*@throwsIllegalArgumentException

*@throwsIllegalAccessException

*@throwsInvocationTargetException*/

private static boolean isDirectory(Preferences root, inthkey, String path)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {return !subKeysForPath(root, hkey, path).isEmpty();

}private static List subKeysForPath(Preferences root, inthkey, String path)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {

List results = new ArrayList();int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {new Integer(hkey), toCstr(path), newInteger(KEY_READ)});if (handles[1] !=REG_SUCCESS)throw new IllegalArgumentException("The system can not find the specified path: '"+getParentKey(hkey)+"\\"+path+"'");int[] info = (int[]) regQueryInfoKey.invoke(root, new Object[] {new Integer(handles[0])});int count = info[0]; //Fix: info[2] was being used here with wrong results. Suggested by davenpcj, confirmed by Petrucio

int maxlen = info[3]; //value length max

for(int index=0; index

results.add(parseValue(valb));

}

regCloseKey.invoke(root,new Object[] {new Integer(handles[0])});returnresults;

}private static int [] createKey(Preferences root, inthkey, String key)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {return (int[]) regCreateKeyEx.invoke(root, new Object[] {newInteger(hkey), toCstr(key)});

}private static void writeStringValue(Preferences root, inthkey, String key, String valueName, String value)throwsIllegalArgumentException, IllegalAccessException, InvocationTargetException {int[] handles = (int[]) regOpenKey.invoke(root, new Object[] {new Integer(hkey), toCstr(key), newInteger(KEY_ALL_ACCESS)});

regSetValueEx.invoke(root,new Object[] {new Integer(handles[0]), toCstr(valueName), toCstr(value)});

regCloseKey.invoke(root,new Object[] {new Integer(handles[0])});

}/*** Makes cmd query for the given hkey and path then executes the query

*@paramhkey

*@parampath

*@returnthe map containing all results in form of key(s) and value(s) obtained by executing query

*@throwsIOException*/

private static Map queryValuesForPath(int hkey, String path) throwsIOException {

String line;

StringBuilder builder= newStringBuilder();

Map map = new HashMap();

Process process= Runtime.getRuntime().exec("reg query \""+getParentKey(hkey)+"\\" + path + "\"");

BufferedReader reader= new BufferedReader(newInputStreamReader(process.getInputStream()));while((line = reader.readLine()) != null) {if(!line.contains("REG_"))continue;

StringTokenizer tokenizer= new StringTokenizer(line, " \t");while(tokenizer.hasMoreTokens()) {

String token=tokenizer.nextToken();if(token.startsWith("REG_"))

builder.append("\t ");elsebuilder.append(token).append(" ");

}

String[] arr= builder.toString().split("\t");

map.put(arr[0].trim(), arr[1].trim());

builder.setLength(0);

}returnmap;

}/*** Determines the string equivalent of hkey

*@paramhkey

*@returnstring equivalent of hkey*/

private static String getParentKey(inthkey) {if(hkey ==HKEY_CLASSES_ROOT)returnCLASSES_ROOT;else if(hkey ==HKEY_CURRENT_USER)returnCURRENT_USER;else if(hkey ==HKEY_LOCAL_MACHINE)returnLOCAL_MACHINE;return null;

}/***Intern method which adds the trailing \0 for the handle with java.dll

*@paramstr String

*@returnbyte[]*/

private static byte[] toCstr(String str) {if(str == null)

str= "";return (str += "\0").getBytes();

}/*** Method removes the trailing \0 which is returned from the java.dll (just if the last sign is a \0)

*@parambuf the byte[] buffer which every read method returns

*@returnString a parsed string without the trailing \0*/

private static String parseValue(bytebuf[]) {if(buf == null)return null;

String ret= newString(buf);if(ret.charAt(ret.length()-1) == '\0')return ret.substring(0, ret.length()-1);returnret;

}

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值