74 GetProcAddressFunc _GetProcAddress;
75 char jvmLib[MAX_LIBNAME_LENGTH]; /* "jvm.dll" */
76 char func1[MAX_FUNC_LENGTH];
77 char func2[MAX_FUNC_LENGTH];
78 char cmd[MAX_CMD_LENGTH]; /* "load", "dump", ... */
79 char arg[MAX_ARGS][MAX_ARG_LENGTH]; /* arguments to command */
80 char pipename[MAX_PIPE_NAME_LENGTH];
81 } DataBlock;
82
83 /*
84 * Return codes from enqueue function executed in target VM
85 */
86 #define ERR_OPEN_JVM_FAIL 200
87 #define ERR_GET_ENQUEUE_FUNC_FAIL 201
88
89
90 /*
91 * Code copied to target process
92 */
93 #pragma check_stack (off)
94 static DWORD WINAPI thread_func(DataBlock *pData)
95 {
96 HINSTANCE h;
97 EnqueueOperationFunc addr;
98
99 h = pData->_GetModuleHandle(pData->jvmLib);
100 if (h == NULL) {
101 return ERR_OPEN_JVM_FAIL;
102 }
103
104 addr = (EnqueueOperationFunc)(pData->_GetProcAddress(h, pData->func1));
105 if (addr == NULL) {
106 addr = (EnqueueOperationFunc)(pData->_GetProcAddress(h, pData->func2));
107 }
108 if (addr == NULL) {
109 return ERR_GET_ENQUEUE_FUNC_FAIL;
110 }
111
112 /* "null" command - does nothing in the target VM */
113 if (pData->cmd[0] == '\0') {
114 return 0;
115 } else {
116 return (*addr)(pData->cmd, pData->arg[0], pData->arg[1], pData->arg[2], pData->pipename);
117 }
118 }
119
120 /* This function marks the end of thread_func. */
121 static void thread_end (void) {
122 }
123 #pragma check_stack
124
125
126 /*
127 * Class: sun_tools_attach_WindowsVirtualMachine
128 * Method: init
129 * Signature: ()V
130 */
131 JNIEXPORT void JNICALL Java_sun_tools_attach_WindowsVirtualMachine_init
132 (JNIEnv *env, jclass cls)
133 {
134 // All following APIs exist on Windows XP with SP2/Windows Server 2008
135 _GetModuleHandle = (GetModuleHandleFunc)GetModuleHandle;
136 _GetProcAddress = (GetProcAddressFunc)GetProcAddress;
137 _IsWow64Process = (IsWow64ProcessFunc)IsWow64Process;
138 }
139
140
141 /*
142 * Class: sun_tools_attach_WindowsVirtualMachine
143 * Method: generateStub
144 * Signature: ()[B
145 */
146 JNIEXPORT jbyteArray JNICALL Java_sun_tools_attach_WindowsVirtualMachine_generateStub
147 (JNIEnv *env, jclass cls)
148 {
149 /*
150 * We should replace this with a real stub generator at some point
151 */
152 DWORD len;
153 jbyteArray array;
154
155 len = (DWORD)((LPBYTE) thread_end - (LPBYTE) thread_func);
156 array= (*env)->NewByteArray(env, (jsize)len);
157 if (array != NULL) {
158 (*env)->SetByteArrayRegion(env, array, 0, (jint)len, (jbyte*)&thread_func);
159 }
160 return array;
161 }
162
163 /*
164 * Class: sun_tools_attach_WindowsVirtualMachine
165 * Method: openProcess
166 * Signature: (I)J
167 */
168 JNIEXPORT jlong JNICALL Java_sun_tools_attach_WindowsVirtualMachine_openProcess
169 (JNIEnv *env, jclass cls, jint pid)
170 {
171 HANDLE hProcess = NULL;
172
173 if (pid == (jint) GetCurrentProcessId()) {
174 /* process is attaching to itself; get a pseudo handle instead */
175 hProcess = GetCurrentProcess();
176 /* duplicate the pseudo handle so it can be used in more contexts */
177 if (DuplicateHandle(hProcess, hProcess, hProcess, &hProcess,
178 PROCESS_ALL_ACCESS, FALSE, 0) == 0) {
|
74 GetProcAddressFunc _GetProcAddress;
75 char jvmLib[MAX_LIBNAME_LENGTH]; /* "jvm.dll" */
76 char func1[MAX_FUNC_LENGTH];
77 char func2[MAX_FUNC_LENGTH];
78 char cmd[MAX_CMD_LENGTH]; /* "load", "dump", ... */
79 char arg[MAX_ARGS][MAX_ARG_LENGTH]; /* arguments to command */
80 char pipename[MAX_PIPE_NAME_LENGTH];
81 } DataBlock;
82
83 /*
84 * Return codes from enqueue function executed in target VM
85 */
86 #define ERR_OPEN_JVM_FAIL 200
87 #define ERR_GET_ENQUEUE_FUNC_FAIL 201
88
89
90 /*
91 * Code copied to target process
92 */
93 #pragma check_stack (off)
94 DWORD WINAPI jvm_attach_thread_func(DataBlock *pData)
95 {
96 HINSTANCE h;
97 EnqueueOperationFunc addr;
98
99 h = pData->_GetModuleHandle(pData->jvmLib);
100 if (h == NULL) {
101 return ERR_OPEN_JVM_FAIL;
102 }
103
104 addr = (EnqueueOperationFunc)(pData->_GetProcAddress(h, pData->func1));
105 if (addr == NULL) {
106 addr = (EnqueueOperationFunc)(pData->_GetProcAddress(h, pData->func2));
107 }
108 if (addr == NULL) {
109 return ERR_GET_ENQUEUE_FUNC_FAIL;
110 }
111
112 /* "null" command - does nothing in the target VM */
113 if (pData->cmd[0] == '\0') {
114 return 0;
115 } else {
116 return (*addr)(pData->cmd, pData->arg[0], pData->arg[1], pData->arg[2], pData->pipename);
117 }
118 }
119
120 /* This function marks the end of jvm_attach_thread_func. */
121 void jvm_attach_thread_func_end (void) {
122 }
123 #pragma check_stack
124
125
126 /*
127 * Class: sun_tools_attach_WindowsVirtualMachine
128 * Method: init
129 * Signature: ()V
130 */
131 JNIEXPORT void JNICALL Java_sun_tools_attach_WindowsVirtualMachine_init
132 (JNIEnv *env, jclass cls)
133 {
134 // All following APIs exist on Windows XP with SP2/Windows Server 2008
135 _GetModuleHandle = (GetModuleHandleFunc)GetModuleHandle;
136 _GetProcAddress = (GetProcAddressFunc)GetProcAddress;
137 _IsWow64Process = (IsWow64ProcessFunc)IsWow64Process;
138 }
139
140
141 /*
142 * Class: sun_tools_attach_WindowsVirtualMachine
143 * Method: generateStub
144 * Signature: ()[B
145 */
146 JNIEXPORT jbyteArray JNICALL Java_sun_tools_attach_WindowsVirtualMachine_generateStub
147 (JNIEnv *env, jclass cls)
148 {
149 /*
150 * We should replace this with a real stub generator at some point
151 */
152 DWORD len;
153 jbyteArray array;
154
155 len = (DWORD)((LPBYTE) jvm_attach_thread_func_end - (LPBYTE) jvm_attach_thread_func);
156 array= (*env)->NewByteArray(env, (jsize)len);
157 if (array != NULL) {
158 (*env)->SetByteArrayRegion(env, array, 0, (jint)len, (jbyte*)&jvm_attach_thread_func);
159 }
160 return array;
161 }
162
163 /*
164 * Class: sun_tools_attach_WindowsVirtualMachine
165 * Method: openProcess
166 * Signature: (I)J
167 */
168 JNIEXPORT jlong JNICALL Java_sun_tools_attach_WindowsVirtualMachine_openProcess
169 (JNIEnv *env, jclass cls, jint pid)
170 {
171 HANDLE hProcess = NULL;
172
173 if (pid == (jint) GetCurrentProcessId()) {
174 /* process is attaching to itself; get a pseudo handle instead */
175 hProcess = GetCurrentProcess();
176 /* duplicate the pseudo handle so it can be used in more contexts */
177 if (DuplicateHandle(hProcess, hProcess, hProcess, &hProcess,
178 PROCESS_ALL_ACCESS, FALSE, 0) == 0) {
|