Multithreading (thread per area) per un server MMO, buona idea?

3

Come progetto personale, sto configurando un MMO e scrivendo il server in C # /. NET Core.

A partire da ora la mia architettura è la seguente: il mondo esiste di diverse aree (puoi andare da un'area all'altra attraverso i portali). Un'area è chiamata "room" sul mio server. Ogni stanza ha la sua lista di clienti (giocatori, ognuno con il loro flusso TCP).

Ora mi stavo chiedendo se fosse ok che eseguissi ogni stanza con il suo thread. Ogni stanza gestirà il proprio ciclo di aggiornamento (loop di gioco / stanza), in quanto è indipendente dalle altre stanze.

La mia preoccupazione è che man mano che il gioco cresce, avrò molte aree e che un thread per area non è un'idea grandiosa.

Quindi la mia domanda è: sto facendo qualcosa di sbagliato o non-benefico in futuro? È meglio avere 1 thread per la logica di gioco per tutte le stanze? O è ok avere un thread per stanza?

    
posta TanguyB 01.10.2018 - 13:43
fonte

3 risposte

7

Separare le sale da gioco in diversi thread è un buon inizio. È consigliabile andare oltre. Quanti dati sono condivisi tra le stanze? Se vengono condivisi pochi dati, è possibile progettare un'API interna (ad esempio chiamate di servizio o tramite un database condiviso) per condividere i dati tra le stanze e fare in modo che ogni stanza sia un processo separato. Ciò faciliterebbe le stanze di hosting su macchine diverse.

Forse ogni stanza può ascoltare il proprio endpoint (indirizzo IP + porta). Quando un giocatore entra in un portale per spostarsi dalla stanza A alla stanza B : process A passa l'oggetto giocatore per elaborare B tramite l'API e il canale interni e contemporaneamente il client di gioco del giocatore apre una nuova connessione all'endpoint in cui il processo B è in ascolto.

I thread possono essere utilizzati per migliorare la concorrenza all'interno di una stanza: la comunicazione con i client di gioco può essere gestita da un pool di thread, separati dal ciclo di gioco principale. La fisica può avere il suo thread. AI può avere il suo thread.

    
risposta data 01.10.2018 - 14:18
fonte
3

Penso che questa potrebbe essere un'architettura valida. La più grande fonte di bug nelle applicazioni multithread è l'accesso condiviso ai dati. Quindi, quando le stanze hanno poca o nessuna comunicazione tra loro e hanno bisogno di poco o nessun accesso ai dati non esplicitamente posseduti da loro, allora sembrano l'ovvio candidato per le unità di parallelizzazione.

Se sei preoccupato della eccessiva parallelizzazione, tieni presente che di solito è più facile ridurre il threading piuttosto che introdurne di più. Quando si scopre che ti piacerebbe gestire le stanze in modo sequenziale dopotutto, di solito non è molto importante uno sforzo di refactoring per cambiare il tuo metodo di aggiornamento per elaborare più stanze in un ciclo invece di uno solo. D'altra parte, tagliando un'architettura single-threaded in una multi-threaded dopo che il fatto può finire rapidamente in un caos buggy.

A proposito, potresti voler organizzare il tuo codice attorno a ThreadPool classifica e passa Task s dove ogni attività consiste nell'esecuzione di un singolo aggiornamento-tick per una singola stanza. Il ThreadPool può essere configurato per utilizzare un numero specifico di thread. Non dovresti impostarlo più alto del numero di core (virtuali) della CPU. Quando si assegnano più attività rispetto ai thread, tali attività verranno accodate ed elaborate non appena viene terminata una discussione. Ciò significa che puoi lasciare la pianificazione degli aggiornamenti al framework.

    
risposta data 01.10.2018 - 16:51
fonte
1

Informazioni importanti sul multithreading:

Conseguenze per la tua architettura:

  • Il threading della stanza sarà molto più piacevole per l'utente: meglio una camera singola leggermente più lenta ma senza ritardi, piuttosto che un singolo thread ultraveloce che consente agli utenti di sperimentare ritardi dovuti a tutte le altre stanze che devono essere elaborate in modo sequenziale maniera !
  • In un MMO, la maggior parte delle volte i tuoi thread attenderanno l'I / O di rete. Questo naturale effetto di attesa (commutazione volontaria) garantisce un migliore utilizzo della CPU e oltre compensa il sovraccarico degli switch di contesto.
  • Tuttavia, il tuo numero massimo di camere sarà limitato . E questo limite è valido anche se le camere più vecchie non sono utilizzate. Se stai pensando a numeri molto lontani, le cifre menzionate, allora ok. Altrimenti dovresti considerare un'altra alternativa.

Alternative:

Il tuo approccio al multithreading è un ottimo inizio. Ma invece di allocare un thread in ogni singola stanza, potresti considerare di avere un thread che gestisce più stanze. Quanti potrebbero essere determinati nella configurazione o calcolati dinamicamente in fase di esecuzione.

Un'altra domanda è come gestisci l'I / O. Le stanze gestiscono le loro connessioni utente? Se no, è meglio allocare più thread per l'I / O e disaccoppiarlo con un'architettura basata su code.

Infine, il problema con le sale multithread è che non puoi scalare oltre il server come MMO della vita reale fare . Quindi è necessario pensare a come ridimensionare tutto questo e come si potrebbe inserire in futuro un gruppo di thread in processi di comunicazione, in modo da poter aggiungere server con processi aggiuntivi per gestire l'aumento del carico di lavoro / connessioni.

    
risposta data 01.10.2018 - 21:03
fonte

Leggi altre domande sui tag