0x00
cTYPES is powerful, and with it we are able to invoke functions in the dynamic link library while creating various complex C data types and underlying operation functions. Python also has the ability to operate in the underlying memory, and with Python's own powerful expressive power, that's why Python is a must-learn programming language for hackers.
0x01 ctypes Use
cTYPES provides three methods to invoke the dynamic-link library: Cdll (), Windll (), and Oledll ().
The difference is in the way the function is called and the return value. Cdll () loads the library whose exported function must use the standard CDECL calling convention.
The Windll () method loads the library whose exported function must use the stdcall calling convention (the native Convention of Win32API).
The Oledll () method is similar to Windll (), but if the function returns an HRESULT error code, you can use the COM function to get a specific error message.
0X02 calling convention
The calling convention refers to the calling method of a function. This includes the method of passing the function parameters, the order (pressing the stack or passing it to the register), and the balance processing of the stack when the function returns.
The following two conventions are most commonly used: Cdecl and stdcall.
cdecl calling convention: the function's parameters are pressed into the stack from right to left, and the caller of the function is responsible for balancing the function after the function is executed. This convention is commonly used in the C language of the x86 architecture.
In C
int Python_rocks (Reason_one,reason_two,reason_three);
In x86 Assembly
push reason_three push reason_two push reason_one call python_rocks add ESP,
From the assembly code above, you can clearly see the parameters of the order of delivery, the last line, the stack pointer increased by 12 bytes (three parameters pass a function, each pushed into the stack of the pointer is 4 bytes, a total of 12
), so that the stack pointer after the function call is restored to the position before the call.
stdcall calling convention: arguments are passed from right to left, but the balance of the stack is done by the function my_socks itself, not by the caller.
In C
int my_socks (color_onecolor_two,color_three);
In x86 Assembly
Push Color_three push color_two push color_one call my_socks
Finally, the return values for both of these calls are stored in EAX.
0x03 How to use
Under Windows:
from ctypes import *="Hello world!\n"msvcrt.printf ( " Testing:%s ", msg)
Under Linux:
from ctypes import *= Cdll ("libc.so.6""Hello, world!\n"libc.printf ("testing:%s", msg)
Using Python to create a C data type is simple enough to make it easy to use components from C or C + +. The following diagram is a good representation of the mapping relationship.
0X04 defines structure and union
In C
Union { long barley_long; int barley_int; Char barley_char[8];} Barley_amount;
In Python
class Barley_amount (Union): = [ ("barley_long", C_long), ("barley_int ", C_int), ("barley_char"8), ]
eg
fromcTYPES Import *classBarley_amount (Union): _fields_= [ ("Barley_long", C_long), ("Barley_int", C_int), ("Barley_char", C_char *8),]value= Raw_input ("Enter The amount of barley to put into the beer VAT:") My_barley= Barley_amount (int(value)) Print"Barley Amount as a long:%ld"%My_barley.barley_longprint"barley Amount as an int:%d"%My_barley.barley_intprint"Barley Amount as a char:%s"% My_barley.barley_char
Output Result:
Enter The amount of barley to put into the the beer VAT: Aslong asint, aschar: B
Assigning a value to a union can be achieved in three different ways. The result of the last Barley_char output is B, because 66 is exactly the ASCII code of B.
Barley_char members are also arrays, an array of eight character sizes. Apply an array in cTYPES, as long as you simply multiply the variable type by the number you want to apply.
Python uses ctypes to implement C library function calls