|
-
Dec 12th, 2012, 01:55 PM
#1
Thread Starter
Lively Member
VB6 to VB.Net
I have a code which I have translated the majority of for use in vb.net.
It requires: 3 Labels, 3 Text Boxes, and 1 Button (named command1)
It also has no errors in the errors list, so hopefully it should be an easy fix for the
average/experienced coder.
CODE: (full)
Code:
Public Class Form1
Structure OSVERSIONINFO
Public dwOSVersionInfoSize As Long
Public dwMajorVersion As Long
Public dwMinorVersion As Long
Public dwBuildNumber As Long
Public dwPlatformId As Long
Public szCSDVersion As String
End Structure
Structure MEMORY_BASIC_INFORMATION ' 28 bytes
Public BaseAddress As Long
Public AllocationBase As Long
Public AllocationProtect As Long
Public RegionSize As Long
Public State As Long
Public Protect As Long
Public lType As Long
End Structure
Structure SYSTEM_INFO ' 36 Bytes
Public dwOemID As Long
Public dwPageSize As Long
Public lpMinimumApplicationAddress As Long
Public lpMaximumApplicationAddress As Long
Public dwActiveProcessorMask As Long
Public dwNumberOrfProcessors As Long
Public dwProcessorType As Long
Public dwAllocationGranularity As Long
Public wProcessorLevel As Integer
Public wProcessorRevision As Integer
End Structure
Private Declare Function GetVersionEx Lib "kernel32" Alias "GetVersionExA" (ByVal LpVersionInformation As OSVERSIONINFO) As Long
Private Declare Function VirtualQueryEx& Lib "kernel32" (ByVal hProcess As Long, ByVal lpAddress As Long, ByVal lpBuffer As MEMORY_BASIC_INFORMATION, ByVal dwLength As Long)
Private Declare Sub GetSystemInfo Lib "kernel32" (ByVal lpSystemInfo As SYSTEM_INFO)
Private Declare Function OpenProcess Lib "kernel32" (ByVal dwDesiredAccess As Long, ByVal blnheritHandle As Long, ByVal dwAppProcessId As Long) As Long
Private Declare Function CloseHandle Lib "kernel32" (ByVal hObject As Long) As Long
Private Declare Function ReadProcessMemory Lib "kernel32" (ByVal hProcess As Long, ByVal lpBaseAddress As Long, ByRef lpBuffer As String, ByVal nSize As Long, ByVal lpNumberOfBytesWritten As Long) As Long
Private Declare Function WriteProcessMemory Lib "kernel32" (ByVal hProcess As Long, ByVal lpBaseAddress As Long, ByRef lpBuffer As String, ByVal nSize As Long, ByVal lpNumberOfBytesWritten As Long) As Long
Private Declare Function GetWindowThreadProcessId Lib "user32" (ByVal hWnd As Long, ByRef lpdwProcessId As Long) As Long
Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As IntPtr
Private Declare Function GetParent Lib "user32" (ByVal hWnd As Long) As Long
Private Declare Function GetWindow Lib "user32" (ByVal hWnd As Long, ByVal wCmd As Long) As Long
Const GW_HWNDNEXT = 2
Private Declare Function InvalidateRect Lib "user32" (ByVal hWnd As Long, ByVal lpRect As Long, ByVal bErase As Long) As Long
Const PROCESS_VM_READ = (&H10)
Const PROCESS_VM_WRITE = (&H20)
Const PROCESS_VM_OPERATION = (&H8)
Const PROCESS_QUERY_INFORMATION = (&H400)
Const PROCESS_READ_WRITE_QUERY = PROCESS_VM_READ + PROCESS_VM_WRITE + PROCESS_VM_OPERATION + PROCESS_QUERY_INFORMATION
Const MEM_PRIVATE& = &H20000
Const MEM_COMMIT& = &H1000
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Try
Me.Text = "Memory Scanner"
Label1.Text = "Start application:"
Label2.Text = "String to find:"
Label3.Text = "Replace with:"
TextBox1.Text = "Calc.exe"
TextBox2.Text = "Backspace"
TextBox3.Text = "VB-O-Matic"
Command1.Text = "&Launch It!"
Catch ex As Exception
MsgBox(ErrorToString, ex.ToString)
End Try
End Sub
Private Sub B1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Command1.Click
Try
Dim pid As Long, hProcess As Long, hWin As Long
Dim lpMem As Long, ret As Long, lLenMBI As Long
Dim lWritten As Long, CalcAddress As Long, lPos As Long
Dim sBuffer As String
Dim sSearchString As String, sReplaceString As String
Dim si As SYSTEM_INFO
Dim mbi As MEMORY_BASIC_INFORMATION
sSearchString = TextBox2.Text
sReplaceString = TextBox3.Text & Chr(0)
pid = Shell(TextBox1.Text) 'launch application (calc.exe in this sample)
hWin = InstanceToWnd(pid) 'get handle of launched window - only to repaint it after changes
'Open process with required access
hProcess = OpenProcess(PROCESS_READ_WRITE_QUERY, False, pid)
lLenMBI = Len(mbi)
'Determine applications memory addresses range
Call GetSystemInfo(si)
lpMem = si.lpMinimumApplicationAddress
'Scan memory
Do While lpMem < si.lpMaximumApplicationAddress
mbi.RegionSize = 0
ret = VirtualQueryEx(hProcess, lpMem, mbi, lLenMBI)
If ret = lLenMBI Then
If ((mbi.lType = MEM_PRIVATE) And (mbi.State = MEM_COMMIT)) Then ' this block is In use by this process
If mbi.RegionSize > 0 Then
sBuffer = mbi.RegionSize
'Read region into string
ReadProcessMemory(hProcess, mbi.BaseAddress, sBuffer, mbi.RegionSize, lWritten)
'Check if region contain search string
lPos = InStr(1, sBuffer, sSearchString, vbTextCompare)
If lPos Then
CalcAddress = mbi.BaseAddress + lPos
Me.Show()
ret = MsgBox("Search string was found at address " & CalcAddress & "." & vbCrLf & "Do you want to replace it?", vbInformation + vbYesNo, "VB-O-Matic")
If ret = vbYes Then
'Replace string in virtual memory
Call WriteProcessMemory(hProcess, CalcAddress - 1, sReplaceString, Len(sReplaceString), lWritten)
'Redraw window
InvalidateRect(hWin, 0, 1)
End If
Exit Do
End If
End If
End If
'Increase base address for next searching cicle. Last address may overhead max Long value (Windows use 2GB memory, which is near max long value), so add Error checking
lpMem = mbi.BaseAddress + mbi.RegionSize
Else
Exit Do
End If
Loop
Catch ex As Exception
MsgBox(ErrorToString, ex.ToString)
End Try
End Sub
Private Function InstanceToWnd(ByVal target_pid As Long) As Long
Try
Dim test_hwnd As Long
Dim test_pid As Long
Dim test_thread_id As Long
test_hwnd = FindWindow(0&, 0&)
Do While test_hwnd <> 0
If GetParent(test_hwnd) = 0 Then
test_thread_id = GetWindowThreadProcessId(test_hwnd, test_pid)
If test_pid = target_pid Then
InstanceToWnd = test_hwnd
Exit Do
End If
End If
test_hwnd = GetWindow(test_hwnd, GW_HWNDNEXT)
Loop
Catch ex As Exception
MsgBox(ErrorToString, ex.ToString)
End Try
End Function
End Class
The errors received when running he application are:
LINE: hProcess = OpenProcess(PROCESS_READ_WRITE_QUERY, False, pid)
Code:
Managed Debugging Assistant 'PInvokeStackImbalance' has detected a problem in 'C:\Documents and Settings\User X\My Documents\Visual Studio 2010\Projects\Memory Scanner\Memory Scanner\bin\Debug\Memory Scanner.vshost.exe'.
Additional Information: A call to PInvoke function 'Memory Scanner!Memory_Scanner.Form1::OpenProcess' has unbalanced the stack. This is likely because the managed PInvoke signature does not match the unmanaged target signature. Check that the calling convention and parameters of the PInvoke signature match the target unmanaged signature.
LINE: Call GetSystemInfo(si)
Code:
An unhandled exception of type 'System.AccessViolationException' occurred in Memory Scanner.exe
Additional information: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
Then the application closes.
What is supposed to do is:
Command1 (Button1) Clicked: Open the calulator, look for the string in backspace,
and change it to VB-O-Matic.
Help is appreciated, Thanks.
-
Dec 12th, 2012, 04:55 PM
#2
Re: VB6 to VB.Net
It's all in your declarations (probably). Try looking them up on pinvoke.net and you'll see that there are some variations of variable type and so on. Even then you might need to experiment a bit.
Having said that, a lot of the stuff that you did in API in VB6 can now be done with native commands in VB.Net. It might be worth, as a learning exercise if nothing else, starting the whole project from scratch.
As the 6-dimensional mathematics professor said to the brain surgeon, "It ain't Rocket Science!"
Reviews: "dunfiddlin likes his DataTables" - jmcilhinney
Please be aware that whilst I will read private messages (one day!) I am unlikely to reply to anything that does not contain offers of cash, fame or marriage!
-
Dec 12th, 2012, 05:35 PM
#3
Thread Starter
Lively Member
Re: VB6 to VB.Net
I changed the openprocess to:
Code:
Private Declare Function OpenProcess Lib "kernel32" (ByVal dwDesiredAccess As Integer, ByVal blnheritHandle As Boolean, ByVal dwAppProcessId As Integer) As IntPtr
Seems to work.. Now I just need to resolve this:
LINE: Call GetSystemInfo(si)
Code:
Additional information: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
Last edited by VBbbq; Dec 12th, 2012 at 06:05 PM.
-
Dec 12th, 2012, 08:38 PM
#4
Re: VB6 to VB.Net
Windows API functions almost exclusively work with 32-bit numbers. In VB6, the Long data type was 32-bit and the Integer data type was 16-bit. In VB.NET, the Long data type is 64-bit and the Integer data type is 32-bit. If you have an API declaration that uses Long then it was almost certainly written for VB6. In VB.NET, you should change the Longs to Integers. Also, whenever a value represents a pointer or a handle, while it's OK to use Integer, it's more correct to use IntPtr.
-
Dec 14th, 2012, 09:45 PM
#5
Thread Starter
Lively Member
Re: VB6 to VB.Net
very helpful info jmcilhinney, i may try to update it again. thanks
Tags for this Thread
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|