int conexionNivel(int iSocketComunicacion, char* sPayload, fd_set* pSetSocketsOrquestador) {

	int iIndiceNivel;

	pthread_mutex_lock(&mtxlNiveles);
	iIndiceNivel = existeNivel(listaNiveles, sPayload);
	pthread_mutex_unlock(&mtxlNiveles);

	if (iIndiceNivel >= 0) {
		tPaquete pkgNivelRepetido;
		pkgNivelRepetido.type   = PL_NIVEL_YA_EXISTENTE;
		pkgNivelRepetido.length = 0;
		enviarPaquete(iSocketComunicacion, &pkgNivelRepetido, logger, "Ya se encuentra conectado al orquestador un nivel con el mismo nombre");
		free(sPayload);
		return EXIT_FAILURE;
	}

	pthread_t *pPlanificador;
	tMensaje tipoMensaje;
	tInfoNivel *pInfoNivel;

	tNivel *pNivelNuevo = (tNivel *)    malloc(sizeof(tNivel));
	pPlanificador 	    = (pthread_t *) malloc(sizeof(pthread_t));
	log_debug(logger, "Se conecto el nivel %s", sPayload);

	char* sNombreNivel = (char *)malloc(strlen(sPayload) + 1);
	strcpy(sNombreNivel, sPayload);
	free(sPayload);

	tPaquete pkgHandshake;
	pkgHandshake.type   = PL_HANDSHAKE;
	pkgHandshake.length = 0;
	enviarPaquete(iSocketComunicacion, &pkgHandshake, logger, "Handshake Plataforma");

	// Ahora debo esperar a que me llegue la informacion de planificacion.
	recibirPaquete(iSocketComunicacion, &tipoMensaje, &sPayload, logger, "Recibe mensaje informacion del nivel");

	pInfoNivel = deserializarInfoNivel(sPayload);
	free(sPayload);

	// Validacion de que el nivel me envia informacion correcta
	if (tipoMensaje == N_DATOS) {

		crearNivel(listaNiveles, pNivelNuevo, iSocketComunicacion, sNombreNivel, pInfoNivel);
		crearHiloPlanificador(pPlanificador, pNivelNuevo);
		delegarConexion(&pNivelNuevo->masterfds, pSetSocketsOrquestador, iSocketComunicacion, &pNivelNuevo->maxSock);
		log_debug(logger, "Nuevo planificador del nivel: '%s' y planifica con: %i", pNivelNuevo->nombre, pNivelNuevo->algoritmo);

		free(sNombreNivel);
		free(pInfoNivel);
		return EXIT_SUCCESS;

	} else {
		log_error(logger,"Tipo de mensaje incorrecto: se esperaba datos del nivel");
		return EXIT_FAILURE;
	}
}
void enviarTurno(tNivel *pNivel, tPersonaje *pPersonaje, int delay) {
	tPaquete pkgProximoTurno;
	pkgProximoTurno.type   = PL_OTORGA_TURNO;
	pkgProximoTurno.length = 0;
	usleep(delay);
	log_debug(logger, "%s: turno al personaje %c", pNivel->nombre, pPersonaje->simbolo);
	enviarPaquete(pPersonaje->socket, &pkgProximoTurno, logger, "Se otorga un turno al personaje");
}
void entregoPosicionRecursoAlPersonaje(tNivel *pNivel, tPersonaje *pPersonajeActual, int iSocketConexion, char* sPayload, t_log* logger) {
	tPaquete pkgPosRecurso;
	obtenerDistanciaFaltante(pPersonajeActual, sPayload);

	pkgPosRecurso.type    = PL_POS_RECURSO;
	pkgPosRecurso.length  = sizeof(int8_t) + sizeof(int8_t);
	memcpy(pkgPosRecurso.payload, sPayload, pkgPosRecurso.length);
	enviarPaquete(pPersonajeActual->socket, &pkgPosRecurso, logger, "Envio de posicion de recurso al personaje");
	free(sPayload);
}
void personajeSolicitaPosicionRecurso(tNivel *pNivel, tPersonaje *pPersonajeActual, int iSocketConexion, char* sPayload, t_log* logger)
{
    tPaquete pkgPosRecurso;
    pkgPosRecurso.type   = PL_POS_RECURSO;
    pkgPosRecurso.length = sizeof(tSimbolo) + sizeof(tSimbolo);
    memcpy(pkgPosRecurso.payload, sPayload, pkgPosRecurso.length);
    free(sPayload);

    enviarPaquete(pNivel->socket, &pkgPosRecurso, logger, "Solicitud al NIVEL la posicion de recurso");
}
void movimientoPersonaje(int iSocketConexion, char* sPayload, tNivel *pNivel, tPersonaje** pPersonajeActual) {

    tMovimientoPers *movPers = deserializarMovimientoPers(sPayload);
    free(sPayload);

	tPaquete pkgMovimientoPers;
	serializarMovimientoPers(PL_MOV_PERSONAJE, *movPers, &pkgMovimientoPers);
	enviarPaquete(pNivel->socket, &pkgMovimientoPers, logger, "Envio movimiento del personaje");

	free(movPers);
}
示例#6
0
void Servidor::darArranque(){
	
	for(int id=0; id < Servidor::getCantidadDeClientesConectados(); id++ ){

			if( (clientes[id].activo) && (clientes[id].socket != INVALID_SOCKET) ){	
				clientes[id].puedeJugar = true;
				enviarPaquete(clientes[id].socket,paqueteArranque,"dale q va");
				Sleep(100);
			}
	}
}
示例#7
0
void Servidor::enviarExplosion(SOCKET s, explosion e){

	string expSerializado;

	expSerializado = StringUtil::int2string((int)e.x);
	expSerializado += separadorCamposArreglo;
	expSerializado += StringUtil::int2string((int)e.y);
	expSerializado += separadorCamposArreglo;
	expSerializado += StringUtil::int2string((int)e.radio);

	enviarPaquete(s, paqueteExplosion, expSerializado);
}
示例#8
0
void Servidor::EnviarSonido(int id, audioEnCola aMandar){

	string sonidoSerializado;
	if(aMandar.reproducir) 
		sonidoSerializado = "1";
	else
		sonidoSerializado = "0";

	sonidoSerializado += separadorCamposArreglo;
	sonidoSerializado += StringUtil::int2string((int)aMandar.s);
	enviarPaquete(clientes[id].socket, paqueteSonido, sonidoSerializado);
}
示例#9
0
void Servidor::actualizar(void* clienteN) 
{
	int id= (int)clienteN;
	audioEnCola** colaDeSonidos;
	int tiempo = 0;

	while(clientes[id].activo){
			
		try{

			recibirDeCliente(&id);
			if(clientes[id].activo){
				enviarCliente(&id, paqueteVista, dibujablesSerializados);

				//recibe los mensajes que mandan otros clientes sin chocar en los threads
				if(time(NULL) - mensaje.tiempoActivo == 0){
					if(mensaje.emisor != clientes[id].socket)
						enviarPaquete(clientes[id].socket, paqueteMensajeInfo, mensaje.msj);
				}else{
					mensaje.tiempoActivo=0;
				}

		
				for(int i=0; i< maxExplosionesPorTurno; i++){
					if(exp[id][i].radio >= 0){
						if(clientes[id].socket != INVALID_SOCKET){
							enviarExplosion(clientes[id].socket, exp[id][i]);
							exp[id][i].radio = -1;
						}
					}
				}
	
				//envio el tiempo del reloj a los clientes:5
				if(Servidor::tiempo != -1 && Servidor::tiempo <= tiempoTurno){ 
					enviarCliente(&id,paqueteTiempo, StringUtil::int2string(Servidor::tiempo));
				}

				colaDeSonidos = Reproductor::getReproductor()->getColaDeEspera();
				for(int i=0; i< numSonidos; i++){
					if(!colaDeSonidos[id][i].enviado){
						EnviarSonido(id, colaDeSonidos[id][i]);
						colaDeSonidos[id][i].enviado = true;
					}
				}
			}
		}catch(exception &e){

			cout<<"catch en Servidor::actualizar: "<<e.what()<<endl;
		}
	}

}
int conexionPersonaje(int iSocketComunicacion, fd_set* socketsOrquestador, char* sPayload) {
	tHandshakePers* pHandshakePers;
	pHandshakePers = deserializarHandshakePers(sPayload);
	free(sPayload);
	int iIndiceNivel;

	log_info(logger, "Se conectó el personaje %c pidiendo el nivel '%s'", pHandshakePers->simbolo, pHandshakePers->nombreNivel);

	pthread_mutex_lock(&mtxlNiveles);
	iIndiceNivel = existeNivel(listaNiveles, pHandshakePers->nombreNivel);

	if (iIndiceNivel >= 0) {
		tNivel *pNivelPedido;
		pNivelPedido = list_get_data(listaNiveles, iIndiceNivel);
		pthread_mutex_unlock(&mtxlNiveles);

		if (pNivelPedido == NULL) {
			log_error(logger, "Saco mal el nivel: Puntero en NULL");
			sendConnectionFail(iSocketComunicacion, PL_NIVEL_INEXISTENTE, "No se encontro el nivel pedido");
		}

		avisoConexionANivel(pNivelPedido->socket, sPayload, pHandshakePers->simbolo);

		add_new_personaje_in_plataforma(pHandshakePers->simbolo);

		agregarPersonaje(pNivelPedido, pHandshakePers->simbolo, iSocketComunicacion);

		free(pHandshakePers->nombreNivel);
		free(pHandshakePers);

		delegarConexion(&pNivelPedido->masterfds, socketsOrquestador, iSocketComunicacion, &pNivelPedido->maxSock);

		pthread_cond_signal(&(pNivelPedido->hayPersonajes));

		tPaquete pkgHandshake;
		pkgHandshake.type   = PL_HANDSHAKE;
		pkgHandshake.length = 0;
		// Le contesto el handshake
		enviarPaquete(iSocketComunicacion, &pkgHandshake, logger, "Handshake de la plataforma al personaje");

		return EXIT_SUCCESS;
	} else {
		pthread_mutex_unlock(&mtxlNiveles);
		log_error(logger, "El nivel solicitado no se encuentra conectado a la plataforma");
		sendConnectionFail(iSocketComunicacion, PL_NIVEL_INEXISTENTE, "No se encontro el nivel pedido");

		free(pHandshakePers->nombreNivel);
		free(pHandshakePers);
		return EXIT_FAILURE;
	}
}
void confirmarMovimiento(tNivel *nivel, tPersonaje *pPersonajeActual) {
	int sockPersonaje = pPersonajeActual->socket;

	if (nivel->algoritmo == RR) {
		pPersonajeActual->quantumUsado++;
		pPersonajeActual->remainingDistance--;
	} else {
		pPersonajeActual->remainingDistance--;
		pPersonajeActual->quantumUsado = 0;
	}
	tPaquete pkgConfirmacionMov;
	pkgConfirmacionMov.type    = PL_CONFIRMACION_MOV;
	pkgConfirmacionMov.length  = 0;
	enviarPaquete(sockPersonaje, &pkgConfirmacionMov, logger, "Se envia confirmacion de movimiento al personaje");

}
示例#12
0
void Servidor::avisarPartidaTerminada(){

	Reproductor::getReproductor()->reiniciar();
	Reproductor::getReproductor()->detenerSonidos();
	Reproductor::getReproductor()->reproducirSonido(VICTORIA);

	for(int id=0; id < Servidor::getCantidadDeClientesConectados(); id++ ){

		if( (clientes[id].activo) && (clientes[id].socket != INVALID_SOCKET) ){	
				
			Sleep(100);
			enviarPaquete(clientes[id].socket,paquetePartidaTerminada,"termino la partida");
			clientes[id].figuras.clear();
			clientes[id].puedeJugar = true;
		}
	}
	clientesConectados = 0;
}
bool avisoConexionANivel(int sockNivel,char *sPayload, tSimbolo simbolo){
//	tMensaje tipoMensaje;
	tSimbolo simboloMsj = simbolo;
	tPaquete *paquete   = malloc(sizeof(tPaquete));
	serializarSimbolo(PL_CONEXION_PERS, simboloMsj, paquete);

	enviarPaquete(sockNivel, paquete, logger, "Envio al nivel el nuevo personaje que se conecto");
//	recibirPaquete(sockNivel, &tipoMensaje, &sPayload, logger, "Recibo confirmacion del nivel");

	free(paquete);

//	if (tipoMensaje == N_CONEXION_EXITOSA) {
//		return true;
//	} else if(tipoMensaje == N_PERSONAJE_YA_EXISTENTE) {
//		return false;
//	}

	return false;
}
示例#14
0
void Servidor::recibirDeCliente(int* clienteN)
{
    Paquete* paquete = new Paquete();
        // data buffer
   char network_data[MAX_PACKET_SIZE];

    // get data for that client
    int data_length = 0;
        int id;
        data_length = red->recibirData(clientes[*clienteN].socket, network_data);
    int cantData = 0;
    while (cantData < data_length)
    {
        paquete->deserializar(&(network_data[cantData]));
                cantData+= paquete->getPesoPaquete();
                switch (paquete->getTipo()) {

            case paqueteInicial:        //en el getMensaje tengo el username
                                id = buscarCliente(paquete->getMensaje());
                                if(id != -1){                                                                           //si existe el username
                                        if(!clientes[id].activo){                                               //si ese username esta congelado

                                                clientes[id].activo=true;                                       //descongelo y doy bienvenida
                                                clientes[id].time=time(NULL);
                                                clientes[id].socket = clientes[*clienteN].socket;
                                                *clienteN = id;

                                                cliente_id--;

                                                //le vuelvo a enviar todas las cosas, por si se reconecta en otra pc
                                                enviarEscenario(*clienteN, true);
                                                enviarImagenes(clientes[*clienteN].socket);
                                                enviarPaquete(clientes[*clienteN].socket, paqueteDescargaLista, "");
                                                cout<<clientes[*clienteN].username<<" se ha reconectado."<<endl;

                                                //hago que el bienvenido le aparezca en la vista al cliente
                                                enviarPaquete(clientes[*clienteN].socket, paqueteMensajeInfo, "Bienvenido de nuevo, "+clientes[*clienteN].username + ".");

                                                //hago que el resto sepa que se reconectó el cliente
                                                //for(int cont=0; cont < escenario->maximosClientes; cont++){
                                                //      if((clientes[cont].username != clientes[*clienteN].username)&&(clientes[cont].activo)){
                                                //              if(clientes[cont].socket != INVALID_SOCKET) enviarPaquete(clientes[cont].socket, paqueteMensajeInfo, clientes[*clienteN].username +" se ha reconectado.");
                                                //      }
                                                //}
                                                mensaje.emisor=clientes[*clienteN].socket;
                                                mensaje.msj = clientes[*clienteN].username +" se ha reconectado.";
                                                mensaje.tiempoActivo=time(NULL);

                                                for (std::list<Gusano*>::const_iterator it = clientes[*clienteN].figuras.begin(); it != clientes[*clienteN].figuras.end(); it++) {
                                                        (*it)->setCongelado(false);
                                                }

												enviarPaquete(clientes[id].socket,paqueteArranque,"dale q va");

                                        }else{                                                                          //si no esta congelado, es xq ya existe un usuario con ese nombre
                                                enviarPaquete(clientes[*clienteN].socket, paqueteFinal, "Ya existe otro usuario con su nombre.");
                                                cliente_id--;
                                                clientes[*clienteN].activo=false;
                                        }
                                }else{                                                                                  //si no existe username, tengo que ver si hay lugar para uno nuevo
                                        if(cliente_id-1 < escenario->maximosClientes){                           //si hay lugar
												
                                                clientes[*clienteN].activo=true;                        //le asigno un espacio y doy la bienvenida
                                                clientes[*clienteN].username = paquete->getMensaje();
                                                clientes[*clienteN].time = time(NULL);

                                                enviarEscenario(*clienteN, false);
                                                enviarImagenes(clientes[*clienteN].socket);
                                                enviarPaquete(clientes[*clienteN].socket, paqueteDescargaLista, "");
                                                cout<<clientes[*clienteN].username<<" se ha conectado."<<endl;
                                                mensaje.tiempoActivo=time(NULL);

                                                //hago que el bienvenido le aparezca en la vista al cliente
                                                enviarPaquete(clientes[*clienteN].socket, paqueteMensajeInfo, "Bienvenido, "+clientes[*clienteN].username + ".");

                                                //hago que el resto sepa que se conectó el cliente
                                                //for(int cont=0; cont < escenario->maximosClientes; cont++){
                                                //      if(clientes[cont].username != clientes[*clienteN].username){
                                                //              if(clientes[cont].socket != INVALID_SOCKET) enviarPaquete(clientes[cont].socket, paqueteMensajeInfo, clientes[*clienteN].username +" se ha conectado.");
                                                //      }
                                                //}
                                                mensaje.emisor=clientes[*clienteN].socket;
                                                mensaje.msj = clientes[*clienteN].username +" se ha conectado.";
                                                mensaje.tiempoActivo=time(NULL);
												clientesConectados++;
                                                //cliente_id++;

                                        }else{
                                                                                                                                //si no hay lugar, lo saco
                                                enviarPaquete(clientes[*clienteN].socket, paqueteFinal, "Ya se ha alcanzado la cantidad maxima de clientes.");
                                                cliente_id--;
                                                clientes[*clienteN].activo=false;
                                        }
                                }
                break;

            case paqueteEvento:
                                if(clientes[*clienteN].username == clientes[Servidor::idJugando].username){
                                        clientes[*clienteN].ultimoEventoSerializado = paquete->getMensaje();
                                }
                                else{
                                        //cout << "espere su turno, ahora esta jugando " << clientes[Servidor::idJugando].username <<endl;
                                        //clientes[*clienteN].ultimoEventoSerializado = paquete->getMensaje();
                                }
                break;

                        case paqueteEstado:
                                        clientes[*clienteN].time = time(NULL);
                                break;

            default: break;
        }

    }
   

        if(clientes[*clienteN].activo){
                if(time(NULL) - clientes[*clienteN].time > 3){  //2 segundos de espera
                       
                        clientes[*clienteN].socket = INVALID_SOCKET;
                        cout<<clientes[*clienteN].username<<" se ha desconectado."<<endl;

                        ////hago que el resto sepa que se desconectó el cliente
                        //for(int cont=0; cont < escenario->maximosClientes; cont++){
                        //      if(clientes[cont].username != clientes[*clienteN].username){
                        //              if(clientes[cont].socket != INVALID_SOCKET) enviarPaquete(clientes[cont].socket, paqueteMensajeInfo, clientes[*clienteN].username +" se ha desconectado.");
                        //      }
                        //}
                        mensaje.emisor=clientes[*clienteN].socket;
                        mensaje.msj = clientes[*clienteN].username +" se ha desconectado.";
                        mensaje.tiempoActivo=time(NULL);

                        for (std::list<Gusano*>::const_iterator it = clientes[*clienteN].figuras.begin(); it != clientes[*clienteN].figuras.end(); it++) {
                                (*it)->setCongelado(true);
                        }
                        clientes[*clienteN].activo=false;
                }
        }
        delete paquete;
}
示例#15
0
void Servidor::enviarCliente(int* clienteN, int tipoPaquete, string mensaje){

		if(clientes[*clienteN].socket != INVALID_SOCKET) enviarPaquete(clientes[*clienteN].socket, tipoPaquete, mensaje);

}
int avisarAlPersonajeDeMuerte(int socketPersonajeMuerto, tSimbolo simbolo, tMensaje tipoDeMuerte){
	tPaquete pkgMuertePers;
	serializarSimbolo(tipoDeMuerte, simbolo, &pkgMuertePers);
	enviarPaquete(socketPersonajeMuerto, &pkgMuertePers, logger, "Envio mensaje de muerte al personaje");
	return EXIT_SUCCESS;
}
void sendConnectionFail(int sockPersonaje, tMensaje typeMsj, char *msjInfo){
	tPaquete pkgPersonajeRepetido;
	pkgPersonajeRepetido.type   = typeMsj;
	pkgPersonajeRepetido.length = 0;
	enviarPaquete(sockPersonaje, &pkgPersonajeRepetido, logger, msjInfo);
}