Estoy resolviendo un desafío de explotación binaria en picoCTF y encontré este código:
((void (*)())buf)();
donde buf
hay una matriz de caracteres.
Resolví el desafío pero parece que no puedo entender exactamente qué está haciendo. Miré este hilo pero no pude distinguirlo.
Que ((void (*)())buf)();
significa
c
function
pointers
function-pointers
sh.3.ll
fuente
fuente
((void (*)())buf)();
significa Significa que el autor no entiendetypedef
.typedef void (*voidFuncPtrType)();
aclararía este código.Respuestas:
void (*)()
es un tipo, siendo el tipo "puntero a la función que toma argumentos indeterminados y no devuelve ningún valor".(void (*)())
es un molde de tipo para el tipo anterior.(void (*)())buf
se lanzabuf
al tipo anterior.((void (*)())buf)()
llama a la función (sin pasar argumentos).En resumen: le dice al compilador que lo trate
buf
como un puntero a una función y que llame a esa función.fuente
cdecl
utilidad (o sitio web ) me parece útil para traducir las expresiones C más complejas al inglés.buf
o dondecopy
se encuentre se encuentra en una dirección ejecutable y el código en sí es independiente de la posición, esto funcionará. Por supuesto, no es tan portátil como parece, pero esto debería funcionar en muchos entornos de metal desnudo, así como en sistemas operativos x86 más antiguos que no establecen el bit de no ejecución (NX) en la pila y el montón.el puntero
buf
se convierte en el puntero para anular la función que toma un número no especificado de parámetros y luego se desreferencia (es decir, la función llamada).fuente
Es un tipo de letra, seguido de una llamada a la función. En primer lugar,
buf
se lanza al puntero a una función que devuelvevoid
. El último par de paréntesis significa que la función se llama.fuente
Convierte la matriz de caracteres en un puntero a una función que no toma argumentos y regresa
void
, y luego la llama. No es necesario desreferenciar el puntero debido a cómo funcionan los punteros de función.Una explicación:
Esa "matriz de caracteres" es en realidad una matriz de código de máquina. Cuando convierte el conjunto a un
void (*)()
y lo llama, ejecuta el código de la máquina dentro del conjunto. Si proporcionó el contenido de la matriz, podría desmontarlo para usted y decirle lo que está haciendo.fuente