Examen diciembre 2018 problema 2 - Sockets

Examen diciembre 2018 problema 2 - Sockets

de Guillermo Angel Kuster Techera -
Número de respuestas: 8

Buenas, mirando este problema me surgieron algunas dudas conceptuales que me gustaria si alguien puede ayudarme a aclarar:

Segun lo que entiendo, un socket es bloqueante cuando el proceso se queda "bloqueado" esperando recibir datos y por contrapartida es no bloqueante cuando se ejecuta de forma inmediata (haya o no datos para obtener).

Por otro lado, la operacion receive() en un socket TCP, devuelve en un string todo lo que haya llegado por TCP hasta ese momento, sin importar si la operacion en cuestion ( receive()) es bloqueante o no. Es esto correcto?

Mi duda surge porque en la solucion del examen, se menciona en forma de comentario :

"leemos el objeto en modo no bloqueante (puede ser muy grande)"
 entonces me pregunto: Que un socket sea bloqueante, implica que como resultado de la operacion receive() todos los datos son leidos? 

Para este caso, todo el documento html está en la variable data, luego de la ejecucion  data, err = socket.receive() si socket es bloqueante?

Disculpas por el entrevero, pero hace varios dias estoy con esto y no logro dar con el clavo.


Muchas gracias.

En respuesta a Guillermo Angel Kuster Techera

Re: Examen diciembre 2018 problema 2 - Sockets

de Jorge Visca -

Lo que ayuda pensar el concepto de bloqueante es el timeout. El timeout es un limite de tiempo que le das a receive() para devolver algo.

timeout=0 (caso "no bloqueante"). El receive() devolverá inmediatamente lo que ya esté en el buffer interno. Si no hay nada, devuelve un string vacío.

timeout>0, el receive() esperará que haya algo de devolver hasta el tiempo indicado. Si aún así no hay nada, devuelve un string vacío.

timeout=-1 ("bloqueante puro"), el receive() esperará hasta que haya algo de devolver, o sea que no devuelve strings vacíos, pero no sabes cuanto tiempo va a quedar trancado.

No podes hacer suposiciones sobre lo que te va a devolver el receive(). Puede ser un byte, puede ser algunos megas (el límite es el tamaño del buffer interno del OS para el socket TCP). Ese problema se puede resolver tanto con sockets bloqueante como no bloqueantes.

Un comentario, lo que lees del socket TCP en ese caso en un objeto HTTP, que incluye un cabezal y un contenido, que puede ser un html o una imagen.


En respuesta a Jorge Visca

Re: Examen diciembre 2018 problema 2 - Sockets

de Guillermo Angel Kuster Techera -

Perfecto, queda clara ahora la diferenciacion de bloqueante y no bloqueante. Respecto a este ejercicio en particular, a que se refiere con el comentario 

"­­ leemos el objeto en modo no bloqueante (puede ser muy grande) " ?

Porque sea el socket bloqueante o no bloqueante, la operacion receive() va a devolver la cantidad de bytes que se encuentren disponibles (con limite el tamano de buffer interno del so) no? Por que se cambia el modo del socket a no bloqueante entonces? Hubiese sido lo mismo dejar el socket como bloqueante en este caso?

Muchas gracias.

En respuesta a Guillermo Angel Kuster Techera

Re: Examen diciembre 2018 problema 2 - Sockets

de Romina Julieta Parada Venossa -
En respuesta a Romina Julieta Parada Venossa

Re: Examen diciembre 2018 problema 2 - Sockets

de Jorge Visca -
En respuesta a Jorge Visca

Re: Examen diciembre 2018 problema 2 - Sockets

de Yamandu Rafael Magallanes Mellognio -

Hola,

En este ejercicio luego de hacer 

m=socket.tcp() 

no habría que hacer 

m.bind(localhost,0)

Para establecer la dirección local del socket?

Gracias

En respuesta a Yamandu Rafael Magallanes Mellognio

Re: Examen diciembre 2018 problema 2 - Sockets

de Jorge Visca -

No es obligatorio ya que después hace 

s = m.connect(host, port)

Al hacer el connect se hace un bind implícito, seleccionando una ip y puerto de forma automática. Aún así es posible hacer un bind manual antes del connect si por alguna razón quisieras asegurarte de usar una IP y puerto en particular (para respetar reglas de un firewall, p.ej.), pero no es el caso.


IMPORTANTE: si bindeas en localhost como en tu ejemplo, ese socket no va poder conectarse a nadie mas que no sea localhost, porque la red de localhost (127.0.0.0/8) no se enruta con nadie.

En respuesta a Jorge Visca

Re: Examen diciembre 2018 problema 2 - Sockets

de Diego Martin Amorena Gomez De Salazar -
Buenas, queria consultar el motivo de setear el timeout bloqueante aqui.
s.settimeout(­-1)
get = "GET "..path..filename.." HTTP/1.0\r\nHost: ”..host..”:”..port..”\r\n"
s.send(get)

Después, el send no se debería haber realizado de una manera análoga a esto?
remain = mi mensaje
while remain
remain err = send remain

Saludos muchas gracias 
En respuesta a Diego Martin Amorena Gomez De Salazar

Re: Examen diciembre 2018 problema 2 - Sockets

de Jorge Visca -
Esa solución en esa parte está mal. Efectivamente, hay que enviar iterando esperando que salga todo.

(Creo que en una versión vieja de la cartilla un socket bloqueante quedaba trancado hasta enviar todo lo que tenía en el send, y la solución está hecha basada en eso. Sin embargo, ese comportamiento de la cartilla vieja era muy bizarro y se cambió por uno más realista)