Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: AlbertoBSD en 13 Septiembre 2016, 20:36 pm



Título: Validando peticion GET manualmente
Publicado por: AlbertoBSD en 13 Septiembre 2016, 20:36 pm
Buen dia estoy desarrollando un pequeño servidor en C para un proyecto que tengo.

Ya tengo buena parte trabajado, pero me gustaria consultarles si existen mas cosas que deba de validar en una peticion GET  el ejemplo que mas o menos tengo del codigo es el siguiente:

Código
  1. #include<stdio.h>
  2. #include<stdlib.h>
  3. #include<string.h>
  4.  
  5. #define KB 1024
  6.  
  7. int main() {
  8. char *type,*resource,*protocol,*extra,*hasQuery,**values = NULL,*key,*value,*aux;
  9. int values_count= 0,i;
  10. char *temp = malloc(KB);
  11. strcpy(temp,"GET /LALALA/xD.txt?q=xD&XD HTTP/1.1");
  12. type = strtok(temp," ");
  13. resource = strtok(NULL," ");
  14. protocol = strtok(NULL," ");
  15. extra = strtok(NULL," ");
  16. printf("type = %p: %s\n",type,type);
  17. printf("resource = %p: %s\n",resource,resource);
  18. printf("protocol = %p: %s\n",protocol,protocol);
  19. printf("extra = %p\n",extra);
  20. hasQuery = strstr(resource,"?");
  21. if(hasQuery) {
  22. printf("query = %p: %s\n",hasQuery,hasQuery);
  23. aux =  strtok(hasQuery+1,"&");
  24. do {
  25. if(aux) {
  26. values = realloc(values,sizeof(char*)*(values_count+1));
  27. values[values_count] = aux;
  28. printf("values: %s\n",values[values_count]);
  29. values_count++;
  30. }
  31. aux =  strtok(NULL,"&");
  32. }while(aux);
  33. i = 0;
  34. while(i < values_count) {
  35. key = strtok(values[i],"=");
  36. value = strtok(NULL,"");
  37. //Aqui salvo los valores key y value para su posterior uso
  38. printf("Key: %s\nValue: %s\n",key,value);
  39. i++;
  40. }
  41. }
  42. else
  43. printf("query = %p\n",hasQuery);
  44. if(values)
  45. free(values);
  46. if(temp) {
  47. free(temp);
  48. }
  49. }
  50.  
  51.  

Estoy releyendo el protocolo del HTTP y estoy validando de momento solo la primera LINEA de la peticion.

Saludos!


Título: Re: Validando peticion GET manualemente
Publicado por: Kaxperday en 13 Septiembre 2016, 21:10 pm
Buenas,

Según veo quieres validar solo la request line y solo para el caso de GET, entonces me parece que la validación puede considerarse correcta, aquí los límites los pones tu si quieres un server de calidad asegurate de hacer un buen control de errores, sino me equivoco todos los HTTP request (incluido el GET por supuesto) tienen en su request line 3 partes: el método, la uri, y la versión de protocolo HTTP empleado, si tienen más o menos de 3 deberías considerar la request como errónea.

Para un GET no veo necesario validar más, ahora deberías de pensar en validar los headers también, e implementar los métodos que deeses y que debes de mostrar cuando te envíen un HTTP OPTIONS.

También cuidado al programar el GET pues por lo general sirve archivos, y pueden hacer algo como "GET ../../passwords.txt HTTP 1.1" y puedan acceder a directorios anteriores que el de la carpeta root del servidor, para ello debes controlar que la uri no empiece con "..", pero eso ya sería más adelante cuando vayas a servir el archivo.

Ánimo con el proyecto, me parece interesante.

Un saludo.


Título: Re: Validando peticion GET manualemente
Publicado por: kub0x en 13 Septiembre 2016, 23:17 pm
Como ejemplo está bien, pero ten cuidado con el parseo/análisis de datos arbitrarios y su consecutivo almacenamiento, pues un buffer overrun podría terminar en consecuencias serias. Por ejemplo podría mandar un paquete que no siguiera el esquema de request de HTTP, sin GET ni POST ni otros.

Lo mejor es seguir el RFC, también te ahorraras cuelgues estilo DOS/DDoS manteniendo la tabla de sesión (socks) en buen estado (apache slowloris que recuerdos).

Saludos!


Título: Re: Validando peticion GET manualemente
Publicado por: AlbertoBSD en 13 Septiembre 2016, 23:27 pm
Muchas gracias por contestar, sabia que te interesaria el topic.

Citar
También cuidado al programar el GET pues por lo general sirve archivos, y pueden hacer algo como "GET ../../passwords.txt HTTP 1.1"

Claro que habia considerado los dotdotpwn... de hecho el recurso siempre lo valido, contra una tabla de recursos validos, si existe lo carga pero con el segundo campo de mi tabla (Un archivo previamente validado con su path valido).

Ya he validado tambien los headers y solo estoy trabajando para leer los datos cuando se trata de un POST, estoy haciendo una pequeña tabla de estados para saber que es lo que sigue y en caso de no coindidir el numero de tokens o alguna otra variable marque error.

Saludos!


Título: Re: Validando peticion GET manualemente
Publicado por: ivancea96 en 13 Septiembre 2016, 23:34 pm
Código
  1. strcpy(temp,"GET /LALALA/xD.txt?q=xD&XD HTTP/1.1");
  2. type = strtok(temp," ");
  3. resource = strtok(NULL," ");
  4. protocol = strtok(NULL," ");
  5. extra = strtok(NULL," ");
  6.  

Como detalle, yo comprobaría que las 3 partes son correctas. Que no tengan caracteres inválidos (como saltos de línea o retornos de carro), y que tanto el "type" como el "protocol" sean válidos; aunque supongo que eso ya lo tendrás en cuenta en el futuro xD

Oh, y yo dejaría de usar ese strtok cuanto antes. Si es un servidor, es probable que pretendas hacerlo multi-thread.


Título: Re: Validando peticion GET manualmente
Publicado por: AlbertoBSD en 14 Septiembre 2016, 00:08 am
Citar
Oh, y yo dejaría de usar ese strtok cuanto antes. Si es un servidor, es probable que pretendas hacerlo multi-thread.

Muy bien acabo de ver los problemas que implica y al parecer no debo de usarlo xD usare strtok_r en su lugar con un 3 parametro para salvar el estado de la funcion.

Saludos