📄 aereg.cpp
字号:
/*
* Created on Apr 16, 2004
* Created by Paul Gardner
* Copyright (C) 2004 Aelitis, All Rights Reserved.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*
* AELITIS, SARL au capital de 30,000 euros
* 8 Allee Lenotre, La Grille Royale, 78600 Le Mesnil le Roi, France.
*
*/
#include "stdafx.h"
#include "aereg.h"
#include "stdio.h"
#include "stdlib.h"
#include "windows.h"
#include "shlwapi.h"
#include "process.h"
#include "shellapi.h"
#include "org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface.h"
#define VERSION "1.2"
HMODULE application_module;
bool non_unicode = false;
UINT uThreadId;
HINSTANCE hInstance;
LRESULT CALLBACK WndProcW(HWND, UINT, WPARAM, LPARAM);
void RegisterWindowClassW();
LRESULT CALLBACK WndProcA(HWND, UINT, WPARAM, LPARAM);
void RegisterWindowClassA();
HRESULT
callback(UINT Msg, WPARAM wParam, LPARAM lParam) ;
JavaVM* jvm;
BOOL APIENTRY
DllMain(
HINSTANCE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved )
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
{
hInstance = hModule;
OSVERSIONINFOA osvi;
application_module = (HMODULE)hModule;
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOA);
GetVersionExA(&osvi);
non_unicode = ( osvi.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS );
if ( non_unicode ){
RegisterWindowClassA();
}else{
RegisterWindowClassW();
}
break;
}
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
CAereg::CAereg()
{
return;
}
void
throwException(
JNIEnv* env,
char* operation,
char* message )
{
jclass except = env->FindClass( "org/gudy/azureus2/platform/win32/access/impl/AEWin32AccessExceptionImpl" );
bool ok = false;
if ( except != NULL ){
jmethodID method = env->GetMethodID( except, "<init>", "(Ljava/lang/String;Ljava/lang/String;)V" );
if ( method != NULL ){
jobject new_object =
env->NewObject( except,
method,
env->NewStringUTF((const char*)operation),
env->NewStringUTF((const char*)message ));
if ( new_object != NULL ){
env->Throw( (jthrowable)new_object );
ok = true;
}
}
}
if ( !ok ){
fprintf( stderr, "AEWin32AccessInterface: failed to throw exception %s: %s\n", operation, message );
}
}
void
throwException(
JNIEnv* env,
char* operation,
char* message,
int error_code )
{
char buffer[4096];
sprintf( buffer, "%s (error_code=%d)", message, error_code );
throwException( env, operation, buffer );
}
HKEY
mapHKEY(
JNIEnv* env,
jint _type )
{
if ( _type == org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_HKEY_CLASSES_ROOT ){
return( HKEY_CLASSES_ROOT );
}else if ( _type == org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_HKEY_CURRENT_CONFIG ){
return( HKEY_CURRENT_CONFIG );
}else if ( _type == org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_HKEY_LOCAL_MACHINE ){
return( HKEY_LOCAL_MACHINE );
}else if ( _type == org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_HKEY_CURRENT_USER ){
return( HKEY_CURRENT_USER );
}else{
throwException( env, "readValue", "unsupported type" );
return( NULL );
}
}
// ******************************
bool
jstringToCharsW(
JNIEnv *env,
jstring jstr,
WCHAR *chars,
int chars_len )
{
if ( jstr == NULL ){
chars[0] = 0;
}else{
int jdata_len = env->GetStringLength(jstr);
if ( jdata_len >= chars_len ){
throwException( env, "jstringToChars", "jstring truncation occurred" );
return( false );
}
const jchar *jdata = env->GetStringChars( jstr, NULL );
for (int i=0;i<jdata_len;i++){
chars[i] = (WCHAR)jdata[i];
}
chars[jdata_len]=0;
env->ReleaseStringChars( jstr, jdata );
}
return( true );
}
// WINDOWS HOOK
void
RegisterWindowClassW()
{
WNDCLASSEXW wcex;
wcex.cbSize = sizeof(WNDCLASSEXW);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProcW;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = 0;
wcex.hCursor = 0;
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
wcex.lpszMenuName = 0;
wcex.lpszClassName = L"Azureus Window Hook";
wcex.hIconSm = 0;
RegisterClassExW(&wcex);
}
LRESULT CALLBACK
WndProcW(
HWND hWnd,
UINT Msg,
WPARAM wParam,
LPARAM lParam)
{
long res = callback( Msg, wParam, lParam );
if ( res != -1 ){
return( res );
}
return DefWindowProcW(hWnd, Msg, wParam, lParam);
}
unsigned WINAPI
CreateWndThreadW(
LPVOID pThreadParam)
{
HWND hWnd = CreateWindowW( L"Azureus Window Hook", NULL, WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT,
NULL, NULL, hInstance, NULL);
if( hWnd == NULL){
printf( "Failed to create window\n" );
return( 0 );
}else{
MSG Msg;
while(GetMessageW(&Msg, hWnd, 0, 0)) {
TranslateMessage(&Msg);
DispatchMessageW(&Msg);
}
return Msg.wParam;
}
}
//
void
RegisterWindowClassA()
{
WNDCLASSEXA wcex;
wcex.cbSize = sizeof(WNDCLASSEXA);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProcA;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = 0;
wcex.hCursor = 0;
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
wcex.lpszMenuName = 0;
wcex.lpszClassName = "Azureus Window Hook";
wcex.hIconSm = 0;
RegisterClassExA(&wcex);
}
LRESULT CALLBACK
WndProcA(
HWND hWnd,
UINT Msg,
WPARAM wParam,
LPARAM lParam)
{
long res = callback( Msg, wParam, lParam );
if ( res != -1 ){
return( res );
}
return DefWindowProcA(hWnd, Msg, wParam, lParam);
}
unsigned WINAPI
CreateWndThreadA(
LPVOID pThreadParam)
{
HWND hWnd = CreateWindowA( "Azureus Window Hook", NULL, WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT,
NULL, NULL, hInstance, NULL);
if( hWnd == NULL){
printf( "Failed to create window\n" );
return( 0 );
}else{
MSG Msg;
while(GetMessageA(&Msg, hWnd, 0, 0)) {
TranslateMessage(&Msg);
DispatchMessageA(&Msg);
}
return Msg.wParam;
}
}
HRESULT
callback(
UINT Msg,
WPARAM wParam,
LPARAM lParam)
{
JNIEnv *env;
if ( jvm->AttachCurrentThread((void **)&env, NULL )){
fprintf( stderr, "failed to attach current thread to JVM\n" );
return( -1 );
}
jclass callback_class = env->FindClass("org/gudy/azureus2/platform/win32/access/impl/AEWin32AccessInterface" );
jlong result = -1;
if ( callback_class != NULL ){
jint j_msg = Msg;
jint j_param1 = wParam;
jlong j_param2 = lParam;
jmethodID method = env->GetStaticMethodID(callback_class, "callback", "(IIJ)J");
result = env->CallStaticLongMethod(callback_class, method, j_msg, j_param1, j_param2 );
}
if ( callback_class != NULL ){
env->DeleteLocalRef( callback_class );
}
jvm->DetachCurrentThread();
return((HRESULT)result );
}
JNIEXPORT void JNICALL
Java_org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_initialise(
JNIEnv *env,
jclass cla )
{
HANDLE hThread;
env->GetJavaVM(&jvm);
if ( non_unicode ){
hThread = (HANDLE)_beginthreadex(NULL, 0, &CreateWndThreadA, NULL, 0, &uThreadId);
}else{
hThread = (HANDLE)_beginthreadex(NULL, 0, &CreateWndThreadW, NULL, 0, &uThreadId);
}
if(!hThread){
throwException( env, "_beginthreadex", "initialisation failed" );
}
}
JNIEXPORT void JNICALL
Java_org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_destroy(
JNIEnv *env,
jclass cla )
{
if ( uThreadId ){
PostThreadMessage(uThreadId, WM_QUIT, 0, 0);
}
}
// UNICODE METHODS
JNIEXPORT jstring JNICALL
Java_org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_getModuleNameW(
JNIEnv *env,
jclass cla )
{
WCHAR buffer[2048];
if ( !GetModuleFileNameW(application_module, buffer, sizeof( buffer ))){
throwException( env, "getModuleName", "GetModuleFileName fails" );
return( NULL );
}
return( env->NewString(buffer, wcslen(buffer)));
}
JNIEXPORT jstring JNICALL
Java_org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_getVersionW(
JNIEnv *env,
jclass cla )
{
jstring result = env->NewStringUTF((char *)VERSION);
return( result );
}
JNIEXPORT jstring JNICALL
Java_org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_readStringValueW(
JNIEnv *env,
jclass cla,
jint _type,
jstring _subkey_name,
jstring _value_name )
{
HKEY key;
HKEY subkey;
WCHAR subkey_name[1024];
WCHAR value_name[1024];
jstring result = NULL;
key = mapHKEY( env, _type );
if ( key == NULL ){
return( NULL );
}
if ( !jstringToCharsW( env, _subkey_name, subkey_name, sizeof( subkey_name ))){
return( NULL );
}
if ( !jstringToCharsW( env, _value_name, value_name, sizeof( value_name ))){
return( NULL );
}
if ( RegOpenKeyW( key, subkey_name, &subkey ) == ERROR_SUCCESS ){
BYTE value[1024];
DWORD value_length = sizeof( value );
DWORD type;
if ( RegQueryValueExW( subkey, value_name, NULL, &type, (unsigned char*)value, &value_length ) == ERROR_SUCCESS){
if ( type == REG_SZ || type == REG_EXPAND_SZ || type == REG_MULTI_SZ ){
if ( type == REG_EXPAND_SZ ){
WCHAR expanded_value[2048];
ExpandEnvironmentStringsW((const WCHAR*)value, expanded_value, sizeof( expanded_value ));
result = env->NewString(expanded_value,wcslen(expanded_value));
}else{
result = env->NewString((const WCHAR*)value,wcslen((WCHAR *)value));
}
}else{
throwException( env, "readValue", "type mismach" );
}
}else{
throwException( env, "readStringValue", "RegQueryValueEx failed" );
}
RegCloseKey(subkey);
}else{
throwException( env, "readStringValue", "RegOpenKey failed" );
}
return( result );
}
JNIEXPORT jint JNICALL
Java_org_gudy_azureus2_platform_win32_access_impl_AEWin32AccessInterface_readWordValueW(
JNIEnv *env,
jclass cla,
jint _type,
jstring _subkey_name,
jstring _value_name )
{
HKEY key;
HKEY subkey;
WCHAR subkey_name[1024];
WCHAR value_name[1024];
jint result = 0;
key = mapHKEY( env, _type );
if ( key == NULL ){
return( NULL );
}
if ( !jstringToCharsW( env, _subkey_name, subkey_name, sizeof( subkey_name ))){
return( NULL );
}
if ( !jstringToCharsW( env, _value_name, value_name, sizeof( value_name ))){
return( NULL );
}
if ( RegOpenKeyW( key, subkey_name, &subkey ) == ERROR_SUCCESS ){
BYTE value[1024];
DWORD value_length = sizeof( value );
DWORD type;
if ( RegQueryValueExW( subkey, value_name, NULL, &type, (unsigned char*)value, &value_length ) == ERROR_SUCCESS){
if ( type == REG_DWORD ){
result = (LONG)value[0];
}else{
throwException( env, "readValue", "type mismach" );
}
}else{
throwException( env, "readStringValue", "RegQueryValueEx failed" );
}
RegCloseKey(subkey);
}else{
throwException( env, "readStringValue", "RegOpenKey failed" );
}
return(result);
}
JNIEXPORT void JNICALL
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -