• Viernes 29 de Marzo de 2024, 09:01

Autor Tema:  Re: Numero maximo de WINSOCK por servidor...  (Leído 5612 veces)

_EL_DJ_LU

  • Miembro activo
  • **
  • Mensajes: 78
    • Ver Perfil
Re: Numero maximo de WINSOCK por servidor...
« en: Sábado 4 de Octubre de 2003, 03:15 »
0
Elabore un programa para un ciber cafe, pero al inicio solo eran 10 maquinas, pero este fue creciendo, ahora tenemos 14 maquinas y pronto aumentaran a unas 20.
Modifique mi programa para 20 maquinas pero no se puede hacer como maximo puedo controlar 16 maquinas si es mas me sale No hay espacio disponible en el búfer.

Lo que hago es: para cada maquina uso un winsock en el servidor, lo que haria 20 winsock.

Alguien me podria ayudar con esto????
Porfa, no se como hacer.
De antemano muchas gracias, espero que esto no sea dificil para ustedes(LOS GRANDES)

observador

  • Miembro activo
  • **
  • Mensajes: 65
    • Ver Perfil
    • http://www.soloprogramacion.net/
Re: Numero maximo de WINSOCK por servidor...
« Respuesta #1 en: Domingo 5 de Octubre de 2003, 03:38 »
0
Bueno... esta semana me ha ido muy mal, la chica me mando al carajo, me enferme, y la proxima semana tengo un examen global (4 unidades de un jalon, todo un semestre en un solo examen), eso sin contar de que hay mucho trabajo en el area donde estoy... Asi que no se porque, pero estoy feliz... y como estoy feliz y como veo que nadie te a contestado, pues yo te contesto... comenzemos...

Bien... Mira, no es necesario incluir un control Winsock por cada cliente que se vaya a conectar al servidor... en lugar de ello podemos utilizar una matriz de controles, y que se vaya agregando o cargando los winsock necesarios para la cantidad requerida de conexiones simultaneas...

Para ello declaramos una variable contador que nos indique cual es el ultimo elemento de matriz que se ha creado...

Esto lo logramos, poniendo en el evento ConnectionRequest del winsock un codigo como el siguiente:

 
Código: Text
  1. Private Sub WinsockServidor_ConnectionRequest(Index As Integer, ByVal requestID As Long)
  2.     If Index = 0 Then
  3.         IntMax = IntMax + 1 'Contador del ultimo cliente que solicito conectarse
  4.        
  5.         Load WinsockServidor(IntMax) 'Crea un nuevo elemento de la matriz de WinsockServidor
  6.         WinsockServidor(IntMax).LocalPort = 0
  7.         WinsockServidor(IntMax).Accept requestID
  8.     End If
  9. End Sub
  10.  
Con esto le asignamos un control Winsock al nuevo cliente que está solicitando conectarse y le aceptamos la conexion...

Para saber y obtener los datos que se reciben de alguno de los clientes conectados solo ustilizaremos el valor de Index, que hace referencia al indice del control creado...

 
Código: Text
  1. Private Sub WinsockServidor_DataArrival(Index As Integer, ByVal bytesTotal As Long)
  2.     Dim CadenaEntrante As String
  3.    
  4.     WinsockServidor(Index).GetData CadenaEntrante 'Obtiene el mensaje entrante segun que control lo envió
  5.     'Aqui procesamos los datos de entrada, que en este ejemplo quedaron
  6.     'almacenados en la variable local CadenaEntrante
  7. End Sub
  8.  
Algo muy importante que debe tomarse en cuenta, sobre todo para aplicaciones que pueden requerir de una gran cantidad de conexiones (simultaneas o no), es la eliminación (cuando ya no este en uso) del elemento de la matriz de Winsocks creado. Con esto, aparte de que liberamos memoria, tambien nos es util para que la aplicación no explote al llegar a un numero elevado de conexiones, que dependiendo del flujo de usuarios esta puede llegar en un par de semanas o inclusive dias (si la aplicacion tiene demasiada concurrencia, como los chats o servidores web, por ejemplo)... Esto lo solucionamos en el evento Close del Winsock  y, como ya he mensionado, hacemos referencia al elemento de la matriz uilizando la variable Index... Veamos el codigo de ejemplo...

 
Código: Text
  1. Private Sub WinsockServidor_Close(Index As Integer)
  2.     WinsockServidor(Index).Close 'Cierras la conexion con el Winsock cliente apuntado por Index
  3.     Unload WinsockServidor(Index) 'Descargas el control de memoria para poder cargarlo de nuevo
  4.                                   'y usarlo más adelante
  5. End Sub
  6.  
Con esto, podremos volver a cargar un elemento ya usado y eliminado... Supongamos que tu aplicacion estara ejecutandose siempre, y que la cantidad máxima de usuarios al dia es de 900. Esto quiere decir que al terminar el cuarto dia de estar funcionando ya habrá ira por el elemento 3600 (mas o menos) de la matriz de controles... y los elementos 1 a 900 ya no existen, entonces podemos volver a crearlos y con esto no llegar al limite establecido (32767), lo cual generaría un error de Desbordamiento. Segun las reglas de Visual Basic, se establece que el máximo número de elementos de una matriz de controles es el 32767, aunque tambien existen otras limitantes que dependen de las caracteristicas de Hardware de la maquina que funge como servidor... tal como la memoria física... pero eso es otra historia...

Asi, por ejemplo, si tu sabes que tu aplicacion no se va a usar por mas de 2000 usuarios simultaneamente (recuerda, puede ser cualquier numero entre 1 y 32767), pues puedes poner ese numero (tal ves configurable) como bandera para reiniciar tu contador. Con esto al codigo del evento ConnectionRequest se le agregaria una linea de mas, quedando algo asi como...

 
Código: Text
  1. Private Sub WinsockServidor_ConnectionRequest(Index As Integer, ByVal requestID As Long)
  2.     If Index = 0 Then
  3.         IntMax = IntMax + 1 'El identificador del ultimo cliente que solicito conectarse
  4.         'Si ya se sobrepasaron 2000 conexiones resetear el contador...
  5.         'Esto es para que se acepten 2000 clientes simultaneameante
  6.         'y al mismo tiempo una cantidad ilimitada de conexeciones
  7.         If IntMax = 2001 Then IntMax = 1 'Linea agregada
  8.        
  9.         Load WinsockServidor(IntMax) 'Crea un nuevo elemento de la matriz de WinsockServidor
  10.         WinsockServidor(IntMax).LocalPort = 0
  11.         WinsockServidor(IntMax).Accept requestID
  12.     End If
  13. End Sub
  14.  
Bueno, en teoria eso es lo necesario para permitir a un servidor ser multiusuario, usando el control Winsock...

Con respecto a la codificacion del programa cliente ésta no cambia en forma brusca con respecto al control Winsock, asi que de eso no te comento nada, ya que como te digo, basicamente no cambia, pues alli no necesitas crear matriz de control ni nada por el estilo... Inclusive, la aplicacion cliente que tienes no sera necerario que la recodifiques al implemantar matriz de Winsock en el Servidor... (a menos que quieras incluir otras caracteristicas claro...)

Mira... Hace algun tiempo hice un chat multiusuario, y aqui te adjunto una copia simplificada de los programas Cliente y Servidor, que este último es el que realmente te interesa...

Aqui te muestro las pantallas de los programas que te adjunto...

Servidor


Cliente


Probando


Como puedes ver en las imagenes, antes de contestarte verifique que el Servidor aceptara varios clientes, para lo cual hice 21 copias del programa cliente y los ejecute para conectarlos todos al servidor y si, como se esperaba, fueron aceptadas todas las solicitudes de conexion y todo transcurrio normalmente...

Bueno, cualquier duda sobre el codigo pues mi correo es santosbussines@hotmail.com

Bueno... me voy, tengo que seguir estudiando para mi examen...
El mensaje contiene 1 archivo adjunto. Debes ingresar o registrarte para poder verlo y descargarlo.
Solo Programacion Net

Hasta pronto...

_EL_DJ_LU

  • Miembro activo
  • **
  • Mensajes: 78
    • Ver Perfil
Re: Numero maximo de WINSOCK por servidor...
« Respuesta #2 en: Sábado 11 de Octubre de 2003, 01:13 »
0
Oe Muchas Gracias, esto me va a servir....

de verdad gracias, pero ahora estoy tratando de establecer comunicacion especificamente con un solo cliente, si no me sale, te paso la voz

GRACIAS...

DJ

_EL_DJ_LU

  • Miembro activo
  • **
  • Mensajes: 78
    • Ver Perfil
Re: Numero maximo de WINSOCK por servidor...
« Respuesta #3 en: Domingo 12 de Octubre de 2003, 02:53 »
0
Ya hice la prueba en conectarme(hablar con un solo cliente) pero no puedo el mensaje siempre le llaga a todos, he tratado de colocarle a cada controlador(index) un localport, pero no se puede, por lo que lo que escribo siempre le llaga a todos...
me podrias decir como puedo hacer para enviarle mensaje a solo un cliente sin que se entere nadie.....

muchas gracias....OBSERVADOR


DJ

HurryCrack

  • Miembro MUY activo
  • ***
  • Mensajes: 206
    • Ver Perfil
Re: Numero maximo de WINSOCK por servidor...
« Respuesta #4 en: Domingo 12 de Octubre de 2003, 13:17 »
0
sabes la ip de cada cliente ke conecta envia la respuesta solo con este.
De todas formas hace ya mas de 6 meses mande un cliente servidor completo, por ke no mirais un poco y vereis ke esta todo, oki? un saludo
:hippi:

observador

  • Miembro activo
  • **
  • Mensajes: 65
    • Ver Perfil
    • http://www.soloprogramacion.net/
Numero maximo de WINSOCK por servidor...
« Respuesta #5 en: Domingo 12 de Octubre de 2003, 19:28 »
0
Bien... esa opcion la tengo programada en el chat que te menciono, pero no pense que tuvieses problemas con ello...

Mira, aunque haya varios usuarios conectados simultaneamente, si es posible enviarle mensajes en forma independiente, para ello, agregale un control CommandButton al servidor... Cambiale el nombre a este CommandButton por CmdPrivado, tambien colocale en la propiedad Caption el texto "Privado" y agregale el siguiente codigo al form del servidor (FrmServidor)...

 
Código: Text
  1. Private Sub CmdPrivado_Click()
  2.     If ListClientes.ListIndex <> -1 Then 'Si hay algún usuario seleccionado
  3.         WinsockServidor(Val(ClientesIndice.List(ListClientes.ListIndex))).SendData "[" & Usuario & "] dijo: " & TxtEnviar.Text
  4.         DoEvents
  5.     else 'Sino hay usuarios, mostrar un mensaje de aviso
  6.         MsgBox "Selecciona a un usuario de la lista" & vbCrLf & "para poder enviarle el mensaje", vbExclamation
  7.     end if
  8.     'Con la siguiente lines desseleccionas el usuario activo
  9.     ListClientes.ListIndex = -1
  10. End Sub
  11.  
Si deseas que los datos que vienen de algun cliente no se redirecciones a todos los demas clientes conectados y que solo sea visto por el servidor, pues solo cambia el codigo del evento WinsockServidor_DataArrival del servidor por el siguiente:

 
Código: Text
  1. Private Sub WinsockServidor_DataArrival(Index As Integer, ByVal bytesTotal As Long)
  2.     Dim Duplicate As Boolean
  3.     Dim CadenaEntrante As String, UsuariosTmp As String
  4.    
  5.     WinsockServidor(Index).GetData CadenaEntrante 'Obtiene el mensaje entrante segun que control lo envió
  6.  
  7.     If InStr(1, CadenaEntrante, " dijo:", 1) = 0 Then
  8.         'Si no esta la frase " dijo:" entonces es que es un nuevo usuario
  9.         ListClientes.AddItem CadenaEntrante 'Agregamos el cliente a la lista
  10.         ClientesIndice.AddItem IntMax       'Agregamos una referencia al winsock que apunte al cliente
  11.        
  12.         TxtMensajes.SelStart = Len(TxtMensajes.Text)
  13.         TxtMensajes.SelText = vbCrLf & "    " & CadenaEntrante & " ha entrado a la sala"
  14.        
  15.         'Ya agregado el usuario, actualizar la lista en los clientes
  16.         UsuariosTmp = "[.LISTA]" & UsuariosConectados
  17.        
  18.         '''El codigo de aqui fue quitado
  19.         '''El codigo que estaba aqui actualizaba la lista de usaurios conectados en todos los clientes
  20.        
  21.         'Mostramos el numero de usuarios que estan conectados
  22.         LblNumUsuarios.Caption = "Conectados: " & ClientesIndice.ListCount
  23.     Else
  24.        
  25.         '''El codigo de aqui fue quitado
  26.         '''El codigo que estaba redireccionaba los datos hacia todos los clientes conectados
  27.        
  28.         TxtMensajes.Text = TxtMensajes.Text & vbCrLf & CadenaEntrante
  29.     End If
  30.     TxtMensajes.SelStart = Len(TxtMensajes.Text)
  31. End Sub
  32.  
Y asi solucionas el problema de como enviarle datos a usuarios especificos... y tambien que no redireccionas los datos que vienen del los clientes...

Si deseas que todos puedan ver los datos que envian los clientes, pero que tambien este la opcion de que pueda enviar mensajes privados al servidor, pues el codigo de el evento WinsockServidor_DataArrival no lo debes cambiar, solo debes de crear un nuevo "comando de servidor" ([.PRIV] por ejemplo) y que este lo reconosca el servidor tal como reconoce el comando [.LIST], por eso no quite la idea basica del procesamiento de comandos para que fuera posible y facil agregarle mas comandos y poder interpretarlos...

Suerte...
Solo Programacion Net

Hasta pronto...

eamc88

  • Nuevo Miembro
  • *
  • Mensajes: 1
    • Ver Perfil
Re: Numero maximo de WINSOCK por servidor...
« Respuesta #6 en: Miércoles 4 de Marzo de 2009, 18:25 »
0
necesito una ayuita para mandar ordenes a otras pcs para con un servidor y varios clientes es para un ciber es proyecto de escuela por favor ayudenme

x_x1_x_x1_x

  • Nuevo Miembro
  • *
  • Mensajes: 1
    • Ver Perfil
Re: Numero maximo de WINSOCK por servidor...
« Respuesta #7 en: Miércoles 7 de Noviembre de 2012, 00:33 »
0
Muchas Gracias, llevo semanas buscando algo como esto.

De verdad, mil millones de gracias.