반응형

유저당 스레드 1개가 맞다. 

하나의 유저를 처리하는동안 다른 유저가 기다리면 랙이 발생한다. 

유저 하나당 스레드 하나가 있어야 스레드가 무슨 작업을 하든 상관없이 다른 유저의 처리를

response 해줄 수 있기 때문.

이를 워커스레드 방식이라고 해서 요청이 들어오면 워커 스레드 하나를 할당해서 작업을 처리.

 

로직 스레드... 네트워크 스레드... 등 용도별로 스레드를 설계

한 로직 스레드에서 이벤트가 발생했을때 여러 클라이언트에게 동시에 보낼 수 있게 된다.

네트워크 리드하는 스레드가 소켓을 퍼오고 큐를 통해 로직스레드로 전달

전달 받은 로직스레드는 이벤트가 생기면 이벤트를 처리한다.

 

클라이언트 - 로직 스레드와 연결

서버는 네트워크 스레드와 연결

 

서버의 네트워크 스레드에서 로직 스레드로 이벤트를 보내줌

로직스레드의 연결되있는 클라이언트들에게 이벤트 전달.(send)

 

send를 할 때도 부하가 걸리고 시간이 걸린다.

이때 보통 많이 쓰는게 IOCP(입출력 완료 포트) 일단 send가 완료될때 까지 기다리지 않고

무조건 다 처리만 해두고? 언제 처리 될지는 모르고? 그래서 로직 스레드는 계속 돌아간다?

네트워크가 따로 처리된다.

 

서버는 보통 로직스레드와 네트워크 스레드로 구별

클라이언트는 단일 스레드를 써도 상관없고 사실 막써도 상관없다? 블로킹도 상괎없고 논블로킹도 상관없다.

동기방식으로 할 경우 sleep 10ms를 해서 초당 10번 네트워크를 체크해도 엄청 빠른거다. 랙또한 안느껴진다.

그래도 비동기가 더 좋은 기술이다. 

 

----------------------------------------------------------------------------------------------------------------

내 질문 : 게임에서 실시간으로 위치를 옮겨주고 싶으면 클라이언트에서 매프레임마다 데이터를 받을려고 하지말고

서버에서 계속 위치를 보내줬어야 하는가?

 

답변 : 위치를 처리하는 방식이 게임마다 다르다. 크게 fps게임과 rpg게임이 있다.

 

RPG : 플레이어가 가고 싶은 방향을 찍으면 아래 그림 처럼 PATH가 생성된다.

이 PATH를 클라이언트에서 만들 수도 있고, 서버에서 만들 수도 있다. 이 PATH정보를 이동속도에 맞춰 이동한다.

PATH가 변경되기 전까지는 서로 정보를 공유하지 않고 PATH가 생성되는 순간 정보를 서로에게 공유한다.

플레이어가 마우스로 가고 싶은 곳을 찍었을때 서버에 이동요청을 보내고 서버는 이동요청 패킷을 접속해있는 유저에게 브로드캐스팅 전파. 그리고 전파받은 클라이언트들은 파란 플레이어가 이동을 시작했고 어디로 가고 직선인지 곡선인지 파악하여 이동 시킨다.

(RPG는 클라이언트가 서버에게 이동요청을 보내고 서버가 검사를 해서(이동속도가 정상인지, 움직일 수 있는 상태인지)검사를 통과하면 위치를 갱신해서 클라이언트 한테 보내주고 클라이언트는 그 위치 정보를 바탕으로 움직이게 된다.)

 

FPS :반응속도가 중요한 게임이다보니 서버한테 이동을 요청하고 응답받아 움직이기에는 느리다.

클라이언트끼리 직접 보낸다.(P2P 방식 그렇기 때문에 클라이언트에서 어느정도 핵을 막아야 한다.)

대부분의 위치정보들을 서버한테 통보하는 형식.

 

----------------------------------------------------------------------------------------------------------------

질문 : rpg 게임과 같은경우에서 플레이어의 위치를 동기화 하는 법은 알았다. 그런데 플레이어가 출발지에서 목적지로 순간이동 해버리는게 아닌 자연스럽게 이동하는 모션을 다른 클라이언트에서도 보여줘야 하는데 방법이 무엇인가?

 

답변 : 이동 패킷(시작점,끝점,이동속도)을

서로 공유한다. 서버가 접속해 있는 유저들한테 다 공유해준다.

1.파란 플레이어가 이동요청을 서버한테 보냄.

2.서버는 파란 플레이어의 이동 패킷을 받고 이동을 허가 시킴과 동시에 파란 플레이어의 근처 플레이어들에게 이동패킷을 보냄.

3.근처 플레이어들은 패킷을 받는 즉시 파란 플레이어를 이동속도 만큼 이동 시킨다.

 

이동하는동안 계속 패킷을 주고 받는 것이 아니라 목표 지점이 바뀔 때만 이동패킷을 주고 받는다.

그리고 이동중에 전투를 하거나 캐릭터가 주는 경우도 있기 때문에,

특정 이벤트가 발생할 때 마다, 서버에 패킷을 전달하고, 서버는 그 패킷을 근처 유저들 한테 다 전달한다.

 

 

서버가 쉽지 않을거라 예상했지만 캐릭터 이동하나에도 필요한 처리가 이렇게 많은것을 보고 절망을 느꼈지만,

교수님 피셜 서버는 채팅서버만 짤 줄 알면된다고 하신다. 게임서버도 채팅서버의 응용일 뿐이라고..

내가 채팅을 보내면 그 채팅이 다른 사람들에게 전달 되듯이, 채팅 패킷을 이동 패킷이나 공격 패킷으로 바꾸기만 하면 그게 곧 게임서버라고 하셨다.

----------------------------------------------------------------------------------------------------------------

질문:

플레이어1과 플레이어2가 있다.

(플레이어1 기준으로 설명)

플레이어1의 화면 기준으로 플레이어2가 움직이면 더미 플레이어2를 움직여 주어

플레이어1의 화면을 업데이트 시켜준다.

나는 위치값만 업데이트 시켜주기위해 아무런 스크립트를 가지고 있지 않은 더미플레이어2를 더미오브젝트로 생성했다.

그런데 만약 여기서 공격기능을 추가하게 되거나, 다른 이벤트를 추가하게 된다면 플레이어2의 공격과 이벤트는 어떻게 수행해야 하는가?

 

답변 :

FPS 방식에서는 내가 말한대로 처리 한다고 한다?

 

그리고

기본적인 서버 방식에서는 스크립트를 동적으로 더미오브젝트에 집어넣거나 서버에 대부분의 3분의 2정도의 기능들을

서버에 작성하여 네트워크로 부터 모든 이벤트가 출발 하도록 네트워크 인터페이스를 먼저 만든다. 

네트워크 인터페이스 클래스를 만들어서 게임의 기능 대부분을 작성한다.

(예 : 아이템 지급, 레벨업, 이동)

 

 

반응형

'네트워크 프로그래밍' 카테고리의 다른 글

IOCP 공부(2)  (0) 2022.05.02
IOCP 공부(1)  (0) 2022.04.30
C# 스레드를 사용한 UDP 서버  (0) 2022.03.23
C# 스레드를 이용한 TCP 서버  (0) 2022.03.23
C# .NET 기반의 네트워크(UDP/IP)(서버)  (0) 2022.03.23