JNIEXPORT jstring JNICALL Java_net_rubygrapefruit_platform_internal_jni_WindowsRegistryFunctions_getStringValue(JNIEnv *env, jclass target, jint keyNum, jstring subkey, jstring valueName, jobject result) { HKEY key = get_key_from_ordinal(keyNum); wchar_t* subkeyStr = java_to_wchar(env, subkey, result); wchar_t* valueNameStr = java_to_wchar(env, valueName, result); DWORD size = 0; LONG retval = SHRegGetValueW(key, subkeyStr, valueNameStr, SRRF_RT_REG_SZ, NULL, NULL, &size); if (retval != ERROR_SUCCESS) { free(subkeyStr); free(valueNameStr); if (retval != ERROR_FILE_NOT_FOUND) { mark_failed_with_code(env, "could not determine size of registry value", retval, NULL, result); } return NULL; } wchar_t* value = (wchar_t*)malloc(sizeof(wchar_t) * (size+1)); retval = SHRegGetValueW(key, subkeyStr, valueNameStr, SRRF_RT_REG_SZ, NULL, value, &size); free(subkeyStr); free(valueNameStr); if (retval != ERROR_SUCCESS) { free(value); mark_failed_with_code(env, "could not get registry value", retval, NULL, result); return NULL; } jstring jvalue = wchar_to_java(env, value, wcslen(value), result); free(value); return jvalue; }
JNIEXPORT jboolean JNICALL Java_net_rubygrapefruit_platform_internal_jni_WindowsRegistryFunctions_getValueNames(JNIEnv *env, jclass target, jint keyNum, jstring subkey, jobject names, jobject result) { wchar_t* subkeyStr = java_to_wchar(env, subkey, result); jclass names_class = env->GetObjectClass(names); jmethodID method = env->GetMethodID(names_class, "add", "(Ljava/lang/Object;)Z"); HKEY key; LONG retval = RegOpenKeyExW(get_key_from_ordinal(keyNum), subkeyStr, 0, KEY_READ, &key); if (retval != ERROR_SUCCESS) { free(subkeyStr); if (retval != ERROR_FILE_NOT_FOUND) { mark_failed_with_code(env, "could open registry key", retval, NULL, result); } return false; } DWORD valueCount; DWORD maxValueNameLen; retval = RegQueryInfoKeyW(key, NULL, NULL, NULL, NULL, NULL, NULL, &valueCount, &maxValueNameLen, NULL, NULL, NULL); if (retval != ERROR_SUCCESS) { mark_failed_with_code(env, "could query registry key", retval, NULL, result); } else { wchar_t* valueNameStr = (wchar_t*)malloc(sizeof(wchar_t) * (maxValueNameLen+1)); for (int i = 0; i < valueCount; i++) { DWORD valueNameLen = maxValueNameLen + 1; retval = RegEnumValueW(key, i, valueNameStr, &valueNameLen, NULL, NULL, NULL, NULL); if (retval != ERROR_SUCCESS) { mark_failed_with_code(env, "could enumerate registry value name", retval, NULL, result); break; } env->CallVoidMethod(names, method, wchar_to_java(env, valueNameStr, wcslen(valueNameStr), result)); } free(valueNameStr); } RegCloseKey(key); free(subkeyStr); return true; }
/* * Marks the given result as failed, using the current value of GetLastError() */ void mark_failed_with_errno(JNIEnv *env, const char* message, jobject result) { mark_failed_with_code(env, message, GetLastError(), result); }
void mark_failed_with_message(JNIEnv *env, const char* message, jobject result) { mark_failed_with_code(env, message, 0, result); }