通过修改COM对象VTable来执行任意函数(真的是任意哦)的研究。希望能有很多人来参加研究
以下是本人代码:
'----------------------- Form1.frm --------------------------------
'需要窗体上放一个名为Command1的按钮控件
Private m_lpVTable As Long
Private m_lpJmp As Long
Private lOldFunc As Long
Private lNewFunc As Long
Private Sub Command1_Click()
Dim oCaller As New CCaller
Dim vRet As Variant
m_lpVTable = GetLngValue(ObjPtr(oCaller))
m_lpJmp = m_lpVTable + &H1C
lOldFunc = GetLngValue(m_lpJmp)
'本地函数测试
'lNewFunc = FuncPtr(AddressOf TestFunction)
'lNewFunc = FuncPtr(AddressOf TestSub)
'外部函数测试
Dim hMod As Long
hMod = LoadLibrary("CallTest.dll")
If hMod <> 0 Then
lNewFunc = GetProcAddress(hMod, "CallInvoke")
If lNewFunc = 0 Then
Debug.Print "no"
Exit Sub
End If
End If
CopyMemory ByVal m_lpJmp, ByVal VarPtr(lNewFunc), 4 'paste in new address
vRet = oCaller.Invoke(123)
MsgBox "返回值:" & vRet
CopyMemory ByVal m_lpJmp, ByVal VarPtr(lOldFunc), 4 'restore old function address
If hMod <> 0 Then
FreeLibrary hMod
End If
End Sub
Private Sub Form_Load()
'防止VB环境崩溃
'Call InitExceptionHandler
End Sub
'----------------------- CCaller.cls --------------------------------
Public Function Invoke(ByVal s As Long) As Long
End Function
'----------------------- mduCaller.bas --------------------------------
Public Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As Long)
Public Declare Function LoadLibrary Lib "kernel32" Alias "LoadLibraryA" (ByVal lpLibFileName As String) As Long
Public Declare Function GetProcAddress Lib "kernel32" (ByVal hModule As Long, ByVal lpProcName As String) As Long
Public Declare Function FreeLibrary Lib "kernel32" (ByVal hLibModule As Long) As Long
Public Function GetLngValue(ByVal lAddress As Long) As Long
CopyMemory GetLngValue, ByVal lAddress, 4
End Function
Public Function TestFunction(ByVal dumb As Long, ByVal s As String) As String
Dim lParaCount As Long
Dim lRetValueAddress As Long
lParaCount = 1
MsgBox "我是快乐的Function"
TestFunction = "Hello"
lRetValueAddress = GetLngValue(VarPtr(dumb) + (lParaCount + 1) * 4)
CopyMemory ByVal lRetValueAddress, ByVal VarPtr(TestFunction), LenB(TestFunction)
End Function
Public Sub TestSub()
MsgBox "我是快乐的Sub"
End Sub
Public Function FuncPtr(ByVal ptr As Long) As Long
FuncPtr = ptr
End Function
'----------------------------------------------------------------------
'----------------------------------------------------------------------
'----------------------------------------------------------------------
'----------------------------------------------------------------------
'----------------------------------------------------------------------
'以下是我C测试函数
void WINAPI CallInvoke(int dumb,int value){
int iParamCount=1;
int** iRetAddress;
iRetAddress =(int **) &dumb+(iParamCount + 1);
**iRetAddress=value;
}