Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   Varios (https://www.clubdelphi.com/foros/forumdisplay.php?f=11)
-   -   Protegiendo tu aplicación contra crackers (https://www.clubdelphi.com/foros/showthread.php?t=91142)

Reasen 18-11-2016 19:47:42

Protegiendo tu aplicación contra crackers
 
Ya estoy bastante harto de ver el 99,9% de las aplicaciones crackeadas... Quiero explicar un poco los métodos que uso para evitarlo. Empecemos.
Esta guía trata de proteger un sistema de licencias basado en seriales conectados online, la protección offline también es posible pero no hablaré de eso aquí (por ahora) porque es mucho más complejo.

Entendiendo porque mis aplicaciones son vulnerables

Veamos un sencillo procedimiento de verificación.
Código Delphi [-]
//Comprobamos en servidor blablablabla
  If licence = false then
  Showmessage('Licencia Incorrecta :(')
  Else
  frmMain.Show;
Desensamblamos el software y nos encontraremos algo como esto
Código PHP:

JE 0x194854 

El cracker solo tendrá que cambiar el JE por JMP que saltará siempre y seremos crackeados.


Implica que nos crackearian por el simple hecho de tocar un byte en memoria, ni siquiera un packer nos puede proteger contra esto porque como bien indica memoria, un packer no puede proteger la memoria, excepto si virtualizas el procedimiento, aun virtualizando el código ensamblador no es suficiente ya que puede dejar el código de frmmain.show mas arriba etc.


En resumen, No hay NADA que puedas hacer si dependes de condiciones.
(No dejo nombres de packers que virtualizan porque sería publicidad, pero es recomendable también virtualizar para complicar más las cosas)

Aplicando la protección mediante strings

Como ya visto anteriormente el cracker va a intentar cambiar el valor false a true para que el software entienda que la licencia es válida, vamos a complicarle la vida…. (risa muy malvada)

“¿Eh pero puedo encriptar todas las strings del software para dejarlo mas seguro?”
Sí pero para debuguear si luego falla algo será “problemático”, recomiendo que uses MadExcept en el proceso, es gratis (no comercial), luego lo desactivas para comercializar y listo.
“¿Pero es demasiado trabajo todo esto, no?”
Sí, por eso tocaría programar un poco unas tools para que cojan las strings y las encripten

Dejo un ejemplo de cómo tendría que ser.
Código Delphi [-]
  Mail := CreateOleObject('CDO.Message');
    Mail.From := UserSMTP;
    Mail.Subject := Title;
    Mail.HTMLBody := BodyText;
    Mail.to := Target;
    Mail.Configuration.Fields.Item('http://schemas.microsoft.com/cdo/configuration/sendusername') := UserSMTP;
  //blablablabla
  

//Ahora encriptamos las strings
   
    Mail := CreateOleObject(DeCryptDataHW(Proc[0]));
    Mail.From := UserSMTP;
    Mail.Subject := Title;
    Mail.HTMLBody := BodyText;
    Mail.to := Target;
    Mail.Configuration.Fields.Item(DeCryptDataHW(Proc[1])) := UserSMTP;

Las strings quedarían así: CDO.Message|http://schemas.microsoft.com/cdo/configuration/sendusername|
Esto se deja en un txt oculto en nuestro servidor.

Entendiendo el funcionamiento del servidor-cliente para la protección

Algoritmo recomendado: RC4, puedes usar AES etc. etc., pero con RC4 ya está bien.Es muy recomendable modificar el algoritmo RC4 ligeramente.


Puedes hacerlo en puro PHP la parte del servidor si te quieres ahorrar un VPS.


Cuando el usuario se loguee correctamente enviaremos las strings encriptadas al clientes basándonos en el HWID de la máquina. Si no haces lo de ir basándote en el HWID el cracker creará un emulador para enviar las mismas peticiones y no sirve de nada.


Dicho esto en cliente(Delphi) desencripta la cadena y luego esplitea las strings
Y la va reponiendo en un array global Proc[0] ..1..2..3


Se puede complicar mucho más todo el procedimiento como incluso hacer que la licencia auto-banee si detecta algo inusual y 100 cosas mas,

estoy dejando lo esencial (idea base) para que saquéis vuestras propias conclusiones.


Ahora el cracker se tiene que romper la cabeza reponiendo una a una cada string…:eek:

movorack 18-11-2016 20:53:11

Muchas gracias por tu aporte

dec 18-11-2016 21:33:07

Hola,

Gracias por tu aporte Reasen. :)

Nota mental: releerlo más despacio. :)

Reasen 18-11-2016 21:33:43

Cita:

Empezado por dec (Mensaje 510980)
Hola,

Gracias por tu aporte Reasen.

Nota mental: releerlo más despacio.

Lo que no entiendas lo puedes preguntar sin problema.

Edit: En otro momento creo que será necesario añadir más detalles o más información, ¿Algún moderador/admin me da permisos para editar el post principal permanentemente?

Casimiro Notevi 19-11-2016 00:53:41

Cita:

Empezado por Reasen (Mensaje 510981)
Edit: En otro momento creo que será necesario añadir más detalles o más información, ¿Algún moderador/admin me da permisos para editar el post principal permanentemente?

Puedes ir ampliando lo que necesites mediante nuevos posts en este mismo hilo. No está permitido editar mensajes transcurridos 30 minutos de su creación.

Reasen 19-11-2016 18:46:57

Cita:

Empezado por Casimiro Notevi (Mensaje 510985)
Puedes ir ampliando lo que necesites mediante nuevos posts en este mismo hilo. No está permitido editar mensajes transcurridos 30 minutos de su creación.

Pues quisiera editar unas cosillas... Pero vale.

dec 19-11-2016 18:56:29

Cita:

Empezado por Reasen (Mensaje 511005)
Pues quisiera editar unas cosillas... Pero vale.

No sabía yo de esa restricción de editar un post luego de 30 minutos... de todas formas puedes añadir más posts. Y, si realmente quieres editar el primer post, por favor, añade un nuevo post a este hilo con lo que quisieras que estuviese en primer lugar... y yo mismo lo pondré ahí.

Reasen 19-11-2016 19:21:50

Cita:

Empezado por dec (Mensaje 511006)
No sabía yo de esa restricción de editar un post luego de 30 minutos... de todas formas puedes añadir más posts. Y, si realmente quieres editar el primer post, por favor, añade un nuevo post a este hilo con lo que quisieras que estuviese en primer lugar... y yo mismo lo pondré ahí.

Quería añadir un ejemplo para evitar inyecciones de DLL a una aplicación Delphi con un sencillo hook y sin usar condiciones. :rolleyes:

Me vendría de perlas tener el botón de editar solamente en este post principal...

Código Delphi [-]
program Project2;


{$APPTYPE CONSOLE}

uses
  SysUtils,
  windows;

procedure hook(target, newfunc: pointer);
var
  jmpto: dword;
  OldProtect: Cardinal; 
begin
  jmpto := dword(newfunc) - dword(target) - 5;
  VirtualProtect(target, 5, PAGE_EXECUTE_READWRITE, @OldProtect);
  pbyte(target)^ := $e9;
  pdword(dword(target) + 1)^ := jmpto;
end;

procedure myLdrLoadDll(PathToFile: PAnsiChar; Flags: variant; ModuleFileName: PAnsiChar; var ModuleHandle: THandle);
begin
  MessageBox(0, 'DLL Detectada!!', 'Nope!', MB_OK);
  ModuleHandle := 0;
  halt;
end;

procedure Maina;
begin
  Hook(GetProcAddress(GetModuleHandle('ntdll.dll'), 'LdrLoadDll'), @myLdrLoadDll);
end;

begin
  Maina;
  readln;
end.

dec 19-11-2016 19:32:20

Hola a todos,

Pero no se puede editar... por buenos motivos... y me temo que no son posibles las excepciones: al menos yo no sabría cómo hacerla. En todo caso acaso estemos hasta "ensuciando" el post... y eso sí que no puede ser... puedes añadir tantos mensajes como quieras a este hilo y abrir otros hilos si lo estimas necesario.

P.D. Lo mismo me pongo yo a editar tu mensaje añadiendo el código de arriba (que ahora miraré) :) y no es lo que tú buscabas o algo... en fin... dejemos las cosas estar, ¡no tocarlo si funciona! :D

Reasen 19-11-2016 19:39:03

Cita:

Empezado por dec (Mensaje 511008)
Hola a todos,

Pero no se puede editar... por buenos motivos... y me temo que no son posibles las excepciones: al menos yo no sabría cómo hacerla.

Bueno, me resulta algo incómodo, pero supongo que no me queda otra. !!!:-|

Casimiro Notevi 19-11-2016 20:19:56

Está bien así, en distintos posts ^\||/
Si hay que hacer alguna corrección se crea un nuevo post, se explica qué se ha modificado y el motivo, y se pone el nuevo código, así queda todo mucho más claro que si se edita el primer mensaje y nadie se entera de que se editó.

Casimiro Notevi 19-11-2016 20:21:38

Además, si ves que puede ser tratado como "truco", tenemos la sección "Trucos", donde también puedes crearlos :)

mamcx 20-11-2016 00:32:10

Cita:

Empezado por Reasen (Mensaje 510966)
Algoritmo recomendado: RC4, puedes usar AES etc. etc., pero con RC4 ya está bien.Es muy recomendable modificar el algoritmo RC4 ligeramente.

Lo peor que pudiste recomendar es alterar un algoritmo criptografico. Eso no se debe hacer.

Ademas, RC4 es mala eleccion:

https://en.wikipedia.org/wiki/RC4

Cita:

While remarkable for its simplicity and speed in software, multiple vulnerabilities have been discovered in RC4, rendering it insecure.[3][4] It is especially vulnerable when the beginning of the output keystream is not discarded, or when nonrandom or related keys are used. Particularly problematic uses of RC4 have led to very insecure protocols such as WEP.
---
Además la seguridad que implementas no es difícil de derrotar, por la misma razón que tu codigo con "IF" lo es. No solo estamos hablando de que se puede hacer un "man in the middle", sino que ademas, es solo cambiar el codigo del ejecutable.

No conozco de un recurso que este al dia sobre este tema, asi que lo unico que se puede recomendar es:

- Nunca inventes tu propia seguridad
- Y menos tu propia criptografía
- Usa las herramientas que provea el OS. Por malas que sean, son mejores de lo que puedes hacer


Y la mejor de todas:

- No confies en ningun tutorial o código aleatorio que salga en internet (mucho menos si no es reciente). Hay que revisar muy bien y elegir solo que se recomienda en el momento.

escafandra 20-11-2016 01:14:40

Cita:

Empezado por escafandra (Mensaje 510624)
Aunque consigas evitar la carga de la dll maliciosa en el arranque de tu app, siempre se puede inyectar con un pequeño ejecutable. Esto quiere decir que no puedes quedarte en la defensa de la carga, has de ir más allá y cambiar el código de protección. Además deberás comprobar, en ese código, que no está cargada una dll no deseada. Puedes usar la API GetModuleFileName para ello pues te da la ruta completa de la dll. También puedes explorar las funciones que exporta. Un hook a la indocumentada LdrLoadDll...

Ha surgido el tema que comenté sobre un Hook a LdrLoadDll. ¿Por qué esa y no LoadLibrary? Pues porque LoadLibrary termina llamando a LdrLoadDll y muchos inyectores optan por esta para saltarse a la primera. Su declaración delphi es como sigue:
Código Delphi [-]
type
PUNICODE_STRING = ^UNICODE_STRING;
UNICODE_STRING = record
  Length: WORD; //USHORT;
  MaximumLength: WORD; //USHORT;
  Buffer: PWCHAR; //PWSTR;
end;

function LdrLoadDll(PathToFile: PWCHAR; Flags: ULONG; ModuleFileName: PUNICODE_STRING; ModuleHandle: PHANDLE): DWORD; stdcall;
UNICODE_STRING es la estructura en el Kernel para el manejo Unicode

Un Hook a LdrLoadDll debe tener en cuenta que afectará a cualquier carga de dll, legal o no, dinámica o estática, con lo que se debe filtrar que dll se puede cargar y cual no.

El problema de los Hooks a las API es que no siempre deben sustituir los 5 primeros bytes, puede que en una versión Windows así sea, pero puede que una actualización cambie esto ligeramente y que el hook haga caer toda la aplicación, esto requiere un mini-desensamblador en tiempo de ejecución. El que tenga interés por el tema puede visitar este tema de hace unos años: HOOK a la API en delphi y en C (trampolín)

Para ilustrar un poco más el asunto anti-inyección podéis leer este otro tema: ¿Protegernos contra inyecciones dll?. Está enfocado a proteger aplicaciones externas pero nada impide hookear nuestra propia aplicación.

Quisiera añadir alguna idea más para los que no quieran depender de la conexión a Internet, puede encriptarse cadenas vitales, incluso fragmentos de código vital, que precisen de la clave del producto para descifrarse, no habrá condicionales pero, claro está, la seguridad dependerá del algoritmo criptográfico usado. Nada es infalible, sólo el aburrimiento del cracker puede dejarnos en paz y quizás estas cosas le aburran.


Saludos.

Reasen 20-11-2016 01:21:47

Cita:

Empezado por mamcx (Mensaje 511014)
Lo peor que pudiste recomendar es alterar un algoritmo criptografico. Eso no se debe hacer.

Ademas, RC4 es mala eleccion:

https://en.wikipedia.org/wiki/RC4



---
Además la seguridad que implementas no es difícil de derrotar, por la misma razón que tu codigo con "IF" lo es. No solo estamos hablando de que se puede hacer un "man in the middle", sino que ademas, es solo cambiar el codigo del ejecutable.

No conozco de un recurso que este al dia sobre este tema, asi que lo unico que se puede recomendar es:

- Nunca inventes tu propia seguridad
- Y menos tu propia criptografía
- Usa las herramientas que provea el OS. Por malas que sean, son mejores de lo que puedes hacer


Y la mejor de todas:

- No confies en ningun tutorial o código aleatorio que salga en internet (mucho menos si no es reciente). Hay que revisar muy bien y elegir solo que se recomienda en el momento.

No es invencible ni es demasiado complicado derrotarla, en eso estoy de acuerdo, debes hacer algo mas por tu cuenta, aunque principalmente le complica mucho las cosas al cracker y de eso se trata.

¿RC4 es tan vulnerable? Recomendaba modificar ligeramente el algoritmo para evitar que el cracker por si obtuviese la clave privada de algún modo no pudiera desencriptar tan fácilmente la información, pero si tan mal está el tema, AES y listo. (No puedo editar el Post principal sino lo rectificaba)

No lo he mirado en ningún lado, idea mia simplemente.

mamcx 20-11-2016 03:48:34

Cita:

Empezado por Reasen (Mensaje 511018)
No es invencible ni es demasiado complicado derrotarla, en eso estoy de acuerdo, debes hacer algo mas por tu cuenta, aunque principalmente le complica mucho las cosas al cracker y de eso se trata.

El asunto es que cuando se habla de estos temas, se debe dar informacion solida o mejor no darla, porque quien carajos sabe lo que esta haciendo?

Cita:

Empezado por Reasen (Mensaje 511018)
¿RC4 es tan vulnerable? Recomendaba modificar ligeramente el algoritmo para evitar que el cracker por si obtuviese

Si no lo sabes, porque lo *recomiendas*? La criptografia es una de las areas donde los inexpertos no deben ni meter la mano ni "innovar" con sus ideas. Es terriblemente complicada.

Ademas, cambiar los algoritmos los puede hacer aun mas debiles. Esos algoritmos toman mucho esfuerzo en desarrollarse. Una desviacion puede eliminar por completo su eficacia.


Cita:

Empezado por Reasen (Mensaje 511018)
No lo he mirado en ningún lado, idea mia simplemente.

Bueno, igual eso mismo hacemos todos. Quien no se ha imaginado que su "esquema de seguridad" es lo maximo? Yo tambien me he puesto en eso. Pero es un error garrafal.

Reasen 20-11-2016 04:01:15

Cita:

Empezado por mamcx (Mensaje 511021)
El asunto es que cuando se habla de estos temas, se debe dar informacion solida o mejor no darla, porque quien carajos sabe lo que esta haciendo?



Si no lo sabes, porque lo *recomiendas*? La criptografia es una de las areas donde los inexpertos no deben ni meter la mano ni "innovar" con sus ideas. Es terriblemente complicada.

Ademas, cambiar los algoritmos los puede hacer aun mas debiles. Esos algoritmos toman mucho esfuerzo en desarrollarse. Una desviacion puede eliminar por completo su eficacia.




Bueno, igual eso mismo hacemos todos. Quien no se ha imaginado que su "esquema de seguridad" es lo maximo? Yo tambien me he puesto en eso. Pero es un error garrafal.

Tomo nota.

escafandra 20-11-2016 23:59:54

Pues fuera como fuere Reasen ha expuesto un tema interesante y si ni los grandes son capaces de controlar las copias piratas, no hay motivo para tratar de buscar soluciones aunque sólo sea para aburrir a un cracker, que al final va a ser los que se busca.

Ransen, te animo a que sigas exponiendo tus opiniones y propuestas, ya sabemos que alguien se las saltará, pero no dejan de ser interesantes por ello. Si hay errores, se comentan, todos los cometemos a diario y seguro que todos sacamos cosas en claro.


Saludos.

mamcx 21-11-2016 00:17:51

Claro, no hay problema con ir exponiendo lo que se sabe. Este es un tema que tiene una representación muy baja entre los desarrolladores y honestamente se requiere mejorar en esto.

Es solo que hay que informarse bien y pisar de a poco.

----

Un area relativamente facil para explorar y que un lenguaje tipado como Delphi trae ventaja es el area reducir las inyecciones de datos. Como en el caso del SQL INJECTION.

Y lo bueno es que es una de las vulnerabilidades mas comunes:

https://www.owasp.org/index.php/Top_10_2013-Top_10
https://www.toptal.com/security/10-m...ulnerabilities

(Estas estan mas enfocados a la web, pero tiene principios generales).


---

El punto clave es que todos las entradas debe validarse y/o convertirse a una estructura de datos mas rigida, en especial si viene de un tipo abierto como una cadena.

Neftali [Germán.Estévez] 21-11-2016 10:19:33

Cita:

Empezado por Reasen (Mensaje 510966)
Quiero explicar un poco los métodos que uso para evitarlo.

Antes de nada agradecerte el aporte Reasen.
Como ya he comentado en el otro hilo donde hemos estado hablando del tema, creo que en "algunos casos" no es aplicable porque necesitas conexión a internet para que la aplicación funcione. Si por la morfología de la aplicación esta es una condición obligatoria, entonces perfecto.


Cita:

Empezado por mamcx (Mensaje 511014)
- Nunca inventes tu propia seguridad

Por experiencia propia puedo decir que a veces un poco de ingenio y de creatividad propia, es mucho mejor que una protección basada en métodos estándar.

Muchos de los cracks que aparecen por ahí se basan en aplicar unos pasos sencillos o en conocer de forma básica 4 herramientas estandard para estos temas. El hecho de hacer "algo diferente" que implica que alguien se tiene que poner a descubrirlo de forma "única para tu programa", en muchos casos "desanima" a quienes quieren hacer un trabajo sencillo y rápido (que son la mayoría).


La franja horaria es GMT +2. Ahora son las 16:25:18.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi