[Lenguaje] : Delphi
[Autor] : Doddy Hackman
[Temario]
-- =================--------
0x01 : Introduccion
0x02 : Creacion del builder
0x03 : Creacion del stub
0x04 : Probando el programa
0x05 : Builder Tools
-- =================--------
0x01 : Introduccion
En este manual les voy a enseñar como hacer un Server Builder en Delphi usando recursos , en el manual anteior les enseñe como hacerlo mediante EOF , algo que no era muy seguro porque los datos estaban en texto plano y se podian leer facilmente , mediante recursos es diferente y para asegurarlo vamos a usar XOR para eso.
Empecemos ...
0x02 : Creacion del builder
Primero vamos hacer el builder , para eso vamos a "File->New->VCL Forms Application" como lo hice en la imagen :
Ahora creamos dos edit y boton con el texto de "Make Server" como en la siguiente imagen :
Despues deben cambiar el titulo del formulario a "Builder" y cambiarle el nombre por defecto que tienen los edits de la siguiente forma :
Edit1 -> ip
Edit2 -> port
Una vez hecho , hacemos doble click en el boton y agregamos el siguiente codigo :
Código
procedure TForm1.Button1Click(Sender: TObject); var archivo: string; // Declaramos la variable "archivo" como string datos: string; // Declaramos la variable "datos" como string clave: integer; // Declaramos la variable "clave" como integer begin archivo := 'stubnow.exe'; // Establecemos la variable "archivo" como el nombre del ejecutable // que vamos abrir datos := '[ip]' + ip.Text + '[ip]' + '[port]' + port.Text + '[port]'; // Establecemos los datos que contiene la IP y el puerto separados por etiquetas // y los guardamos en la variable "datos" clave := 123; // Establecemos la variable "clave" como "123" escribir_recurso(archivo, datos, clave); // Escribimos el recurso usando la funcion // "escribir_recurso" usando como argumentos las variables que acabamos de establecer ShowMessage('Done'); // Mostramos un mensaje en pantalla end;
Fuera del codigo de la funcion "click" del boton agregamos el codigo de estas dos funciones :
Código
function xor_now(texto: string; clave: integer): string; // Funcion xor_now con el argumento // del texto a crifrar y la clave a usar var numero: integer; // Declaramos la variable "numero" como entero contenido: string; // Declaramos la variable "contenido" como string begin contenido := ''; // Vaciamos la variable contenido for numero := 1 to Length(texto) do // Realizamos un for del "1" // a la longitud de la variable texto begin contenido := contenido + Char(integer(texto[numero]) xor clave); // Realizamos el cifrado xor end; Result := contenido; // Devolvemos como resultado la variable "contenido" end; function escribir_recurso(ruta: string; datos: string; clave: integer): bool; var escribiendo: THandle; // Declaramos la variable "escribiendo" como THandle begin datos := xor_now('-0x646F646479206861636B6D616E-' + datos + '-0x646F646479206861636B6D616E-', clave); // Ciframos los datos usando la funcion xor_now // Los parametros que usamos en la funcion xor_now son la variable "datos" como el texto // a cifrar , los "datos" estan entre dos delimitadores para facilitar su busqueda y // tambien usamos la variable "clave" como key en el cifrado xor escribiendo := BeginUpdateResource(pchar(ruta), False); // Empezamos el inicio de de la creacion // del recurso usando la variable "ruta" UpdateResource(escribiendo, MakeIntResource(10), 'CONFIGURATION', 0, pchar(datos), (Length(datos) + 1) * SizeOf(datos[1])); // Escribimos el recurso usando // la variable "datos" como el contenido del recurso y como nombre del recurso usamos // "CONFIGURATION" EndUpdateResource(escribiendo, False); // Terminamos de crear el recurso Result := True; // Devolvemos True como resultado de la funcion end;
Les deberia quedar algo asi :
Con eso ya estaria el builder entonces guardamos el proyecto como "builder_now" o como quieran para terminar el builder.
0x03 : Creacion del stub
Ahora vamos a codear el Stub para eso vamos a "File->New->VCL Forms Application" como lo hice en la imagen :
La idea es buscar el recurso en el ejecutable mismo , entonces para eso vamos a crear dos edits y un boton con el texto de "Get Values".
Despues deben poner como titulo del formulario "Stub" y cambiar los names de los edits de la siguiente forma :
Edit1 -> ip
Edit2 -> port
El formulario les deberia quedar algo asi :
Ahora hacemos doble click en el boton y ponemos el siguiente codigo :
Código
procedure TForm1.Button1Click(Sender: TObject); var clave: integer; // Declaramos la variable "clave" como integer datos: string; // Declaramos la variable "datos" como string ip_found: string; // Declaramos la variable "ip_found" como string port_found: string; // Declaramos la variable "port_found" como string begin clave := 123; // Establecemos la variable "clave" como 123 datos := leer_recurso(clave); // Leemos el recurso usando el key que esta // en la variable clave y guardamos los datos en la variable "datos" ip_found := regex(datos, '[ip]', '[ip]'); // Usamos la funcion regex() para buscar // la ip y la guardamos en la variable "ip_found" port_found := regex(datos, '[port]', '[port]'); // Usamos la funcion regex() para // buscar el puerto y lo guardamos en la variable "port_found" ip.text := ip_found; // Mostramos en el edit "ip" la IP port.text := port_found; // Mostramos en el edit "port" el puerto ShowMessage('Loaded'); // Mostramos en pantalla un mensaje end;
Despues ponemos las siguientes funciones fuera del codigo del boton :
Código
function regex(text: string; deaca: string; hastaaca: string): string; begin Delete(text, 1, AnsiPos(deaca, text) + Length(deaca) - 1); SetLength(text, AnsiPos(hastaaca, text) - 1); Result := text; end; function xor_now(texto: string; clave: integer): string; // Funcion xor_now con el argumento // del texto a crifrar y la clave a usar var numero: integer; // Declaramos la variable "numero" como entero contenido: string; // Declaramos la variable "contenido" como string begin contenido := ''; // Vaciamos la variable contenido for numero := 1 to Length(texto) do // Realizamos un for del "1" // a la longitud de la variable texto begin contenido := contenido + Char(integer(texto[numero]) xor clave); // Realizamos el cifrado xor end; Result := contenido; // Devolvemos como resultado la variable contenido end; function leyendo_recurso: string; var leyendo1: HRSRC; // Establecemos la variable "leyendo1" como HRSRC leyendo2: DWORD; // Establecemos la variable "leyendo2" como DWORD leyendo3: THandle; // Establecemos la variable "leyendo3" como THandle leyendo4: pointer; // Establecemos la variable "leyendo4" como Pointer begin leyendo1 := FindResource(hInstance, 'CONFIGURATION', RT_RCDATA); // Buscamos el recurso // "CONFIGURATION" leyendo2 := SizeofResource(hInstance, leyendo1); // Calculamos la tamaño del recurso leyendo3 := LoadResource(hInstance, leyendo1); // Cargamos el recurso leyendo4 := LockResource(leyendo3); // Bloqueamos el recurso para poder leerlo despues if leyendo4 <> nil then // Si "leyendo4" no esta null ... begin SetLength(Result, leyendo2 - 1); // Cambiamos la longitud de Result CopyMemory(@Result[1], leyendo4, leyendo2); // Copiamos los datos al resultado de la funcion FreeResource(leyendo3); // Liberamos el recurso end; end; function leer_recurso(clave: integer): string; var datos: string; // Declaramos la variable "datos" como string begin datos := xor_now(leyendo_recurso, clave); // Realizamos el cifrado xor con los datos que usamos // como argumentos de la funcion leer_recurso() datos := regex(datos, '-0x646F646479206861636B6D616E-', '-0x646F646479206861636B6D616E-'); // Usamos la funcion regex() para cortar los delimitadores // y encontrar asi los datos del recurso para despues guardar el // resultado en la variable "datos" Result := datos; // Devolvemos como resultado lo que contiene la variable "datos" end;
El codigo les deberia quedar asi :
Guardan el proyecto con el nombre que quieran y con eso ya estaria listo el stub.
0x04 : Probando el programa
Para probarlo cargamos el builder y llenamos los campos de IP y Puerto como quieran , un ejemplo de como los complete yo seria :
Despues presionan el boton "Make Server" y listo.
Ahora cargamos el stub y le damos al boton "Get Values" , deberian ver como resultado algo como esto :
Si no ven algo como en la imagen es porque hicieron algo mal en el codigo.
0x05 : Builder Tools
Como regalo les dejo esta Unit que hice en Delphi sobre como hacer un Builder , contiene funciones para EOF y Recursos , en los dos casos uso XOR para cifrar los datos , tambien viene con ejemplos de uso.
Solo deben agregar "builder_tools" en el parte de "uses" del codigo y listo , podran usar las funciones.
El codigo :
Código
// Unit : Builder Tools // Version : 0.2 // (C) Doddy Hackman 2015 // Credits : Resources based in http://www.hackforums.net/showthread.php?tid=1422700 // Examples : // escribir_eof('stub.exe','-delimitador-','-delimitador-','test',123); // leer_eof('stub.exe','-delimitador-','-delimitador-',123); // escribir_recurso('stub.exe','test',123); // leer_recurso(123); unit builder_tools; interface uses SysUtils, Windows; function leer_eof(ruta, delimitador1, delimitador2: string; clave: integer): string; function escribir_eof(ruta, delimitador1, delimitador2, texto: string; clave: integer): bool; function escribir_recurso(ruta: string; datos: string; clave: integer): bool; function leyendo_recurso: string; function leer_recurso(clave: integer): string; function xor_now(texto: string; clave: integer): string; function regex(text: string; deaca: string; hastaaca: string): string; implementation function xor_now(texto: string; clave: integer): string; var numero: integer; contenido: string; begin contenido := ''; for numero := 1 to Length(texto) do begin contenido := contenido + Char(integer(texto[numero]) xor clave); end; Result := contenido; end; function regex(text: string; deaca: string; hastaaca: string): string; begin Delete(text, 1, AnsiPos(deaca, text) + Length(deaca) - 1); SetLength(text, AnsiPos(hastaaca, text) - 1); Result := text; end; function leer_eof(ruta, delimitador1, delimitador2: string; clave: integer): string; var ob: THandle; code: Array [0 .. 9999 + 1] of Char; nose: DWORD; resultado: string; begin ob := INVALID_HANDLE_VALUE; code := ''; ob := CreateFile(pchar(ruta), GENERIC_READ, FILE_SHARE_READ, nil, OPEN_EXISTING, 0, 0); if (ob <> INVALID_HANDLE_VALUE) then begin SetFilePointer(ob, -9999, nil, FILE_END); ReadFile(ob, code, 9999, nose, nil); CloseHandle(ob); end; resultado := regex(code, delimitador1, delimitador2); resultado := xor_now(resultado, clave); Result := resultado; end; function escribir_eof(ruta, delimitador1, delimitador2, texto: string; clave: integer): bool; var linea: string; aca: THandle; code: Array [0 .. 9999 + 1] of Char; nose: DWORD; marca_uno: string; marca_dos: string; begin aca := INVALID_HANDLE_VALUE; nose := 0; begin linea := delimitador1 + xor_now(texto, clave) + delimitador2; StrCopy(code, pchar(linea)); aca := CreateFile(pchar(ruta), GENERIC_WRITE, FILE_SHARE_READ, nil, OPEN_EXISTING, 0, 0); if (aca <> INVALID_HANDLE_VALUE) then begin SetFilePointer(aca, 0, nil, FILE_END); WriteFile(aca, code, 9999, nose, nil); CloseHandle(aca); Result := True; end else begin Result := False; end; end; end; function escribir_recurso(ruta: string; datos: string; clave: integer): bool; var escribiendo: THandle; begin datos := xor_now('-0x646F646479206861636B6D616E-' + datos + '-0x646F646479206861636B6D616E-', clave); escribiendo := BeginUpdateResource(pchar(ruta), False); UpdateResource(escribiendo, MakeIntResource(10), 'CONFIGURATION', 0, pchar(datos), (Length(datos) + 1) * SizeOf(datos[1])); EndUpdateResource(escribiendo, False); Result := True; end; function leyendo_recurso: string; var leyendo1: HRSRC; leyendo2: DWORD; leyendo3: THandle; leyendo4: pointer; begin leyendo1 := FindResource(hInstance, 'CONFIGURATION', RT_RCDATA); leyendo2 := SizeofResource(hInstance, leyendo1); leyendo3 := LoadResource(hInstance, leyendo1); leyendo4 := LockResource(leyendo3); if leyendo4 <> nil then begin SetLength(Result, leyendo2 - 1); CopyMemory(@Result[1], leyendo4, leyendo2); FreeResource(leyendo3); end; end; function leer_recurso(clave: integer): string; var datos: string; begin datos := xor_now(leyendo_recurso, clave); datos := regex(datos, '-0x646F646479206861636B6D616E-', '-0x646F646479206861636B6D616E-'); Result := datos; end; end. // The End ?
Eso seria todo.
--========--
The End ?
--========--
Version PDF.
Version en VideoTutorial :