묻고 답해요
144만명의 커뮤니티!! 함께 토론해봐요.
인프런 TOP Writers
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
안녕하세요 루키스님. 클라 연동에 관해서 질문을 드리고 싶습니다.
안녕하세요 루키스님.제가 비쥬얼 스튜디오에서 윈도우 어플리케이션을 만들어서 DX11포폴을 만들고 서버를 연동하려고 시도중입니다. 이 상황에서 wWinMain에 ClientServiceRef service = MakeShared<ClientService>( NetAddress(L"127.0.0.1", 7777), MakeShared<IocpCore>(), MakeShared<ServerSession>, // TODO : SessionManager 등 1); ASSERT_CRASH(service->Start()); GThreadManager->SetFlags(1); for (int32 i = 0; i < 2; i++) { GThreadManager->Launch([=]() { while (true) { service->GetIocpCore()->Dispatch(10); } }); } //밑은 DX11을 작동시켜주기 위한 함수들입니다. while (true) { if (PeekMessage(&msg, nullptr, 0, 0, PM_REMOVE)) { if (WM_QUIT == msg.message) break; if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg)) { TranslateMessage(&msg); DispatchMessage(&msg); } } else { CEngine::GetInst()->progress(); CEditorObjMgr::GetInst()->progress(); ImGuiMgr::GetInst()->progress(); // 렌더 종료 CDevice::GetInst()->Present(); } }이렇게 쓰레드를 생성해서 작동을 시켜주었습니다.그런데 생성된 게임 윈도우에서 X키를 눌러서 프로그램을 강제로 종료시켰는데, 이 메인 쓰레드 자체는 정상적으로 WM_DESTROY를 호출 받아서 종료되었는데, 멀티 쓰레드들이 멈추지 않고 계속 돌아 프로그램이 종료되지 않고, 좀비처럼 살아남는 현상이 계속되고 있습니다.쓰레드를 강제로 종료시키니 메모리 릭이 남고, 어떻게 문제를 해결해야할지 해결책을 찾지 못해서 이렇게 질문 남깁니다.참고) 루키스님의 패킷 직렬화#3 코드를 참조해서 만들고 있습니다!감사합니다.
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
비동기를 제대로 이해했는지 궁금합니다
1) 제가 제대로 비동기 방식을 이해한게 맞는지 궁금합니다. 비동기 방식이 어떤 함수를 호출한다면 함수를 지금 바로 처리하지 않고 예약같은 개념으로 요청한 함수를 나중에 처리하고 그동안 요청한 함수외에 다른 부분을 실행하는걸로 이해를 했는데 맞는건지 궁금합니다.2) 만약에 제가 이해한 방식대로 비동기가 진행이 된다면 수업에서 진행한 ::WSAWaitForMultipleEvents(1, &wsaEvent, TRUE, WSA_INFINITE, FALSE); 코드에서 블로킹 방식처럼 진행하는데 이 부분은 비동기와는 맞지 않는 부분아닌가요??
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
데드락 탐지
데드락 탐지에 관련해서 궁금한게 있어서 질문드립니다.아래의 코드로 lock_guard를 이용해서 데드락을 탐지 하려고하는데 데드락이 되는 상황이 발생하고, 탐지는 안되는 경우가 가끔 발생하네요... DeadLockProfiler는 예제의 코드를 복사해서 사용했습니다. #include "pch.h" #include <iostream> #include "DeadLockProfiler.h" mutex lock1; mutex lock2; void Test(); void Test2(); void Test() { DeadLockProfiler::GetInst()->PushLock("Test"); lock_guard<mutex> gurad(lock1); Test2(); DeadLockProfiler::GetInst()->PopLock("Test"); } void Test2() { DeadLockProfiler::GetInst()->PushLock("Test2"); lock_guard<mutex> gurad(lock2); Test(); DeadLockProfiler::GetInst()->PopLock("Test2"); } int main() { thread th1([=] { while (1) { cout << "test" << endl; Test(); this_thread::sleep_for(100ms); } }); thread th2([=] { while (1) { cout << "test2" << endl; Test2(); this_thread::sleep_for(100ms); } }); th1.join(); th2.join(); return 0; }
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
템플릿 흑마법을 보고 질문 글을 남깁니다.
Job Queue #2의 영상을 보고 질문드립니다.이 영상을 보고 저번에 메모리 관련해서도 보고 느낀 것인데, 템플릿 흑마법을 따로 공부할 수 있는 책이나 가이드가 있을까요?루키스님의 영상을 볼 때는 템플릿 흑마법이 이해가 가긴 하는데, 이걸 스스로 짤 생각을 하니 도저히 엄두가 안나서 공부가 필요할 것 같아 이렇게 질문 글을 남깁니다.
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
혹시 언리얼 클라에서는 WSA Recv가 아니라 그냥 recv 사용해야 하나요?
서버랑 언리얼 연동 후 단순한 데이터 교환은 되는데, 패킷을 받아 스폰 기능을 사용하려고 하면 IsInGameThread() 라는 에러가 뜹니다. 대충 느낌을 보아하니 뭔가 외부 쓰레드? 그런 걸 차단하는 느낌이 드는데...Dispatch 해주는 워커쓰레드한테 FRunable 해줘도 해결 되지 않아서 질문 드립니다.. 혹시 다른 사람은 어떤가 싶어, 코드를 보니 서버는 IOCP를 사용하되, 언리얼에서는 그냥 recv만 사용하더군요.
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
강의에서 allocate 함수 두번 호출되는 것에 대해
강의 7:26 초 쯤에서의vector<Knight, StlAllocator<Knight> v(100);이후 allocate 함수 호출 과정에서 처음에 1, 두번째 100이 호출 되는 이유는 무엇인가요?
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
Server Service에서 함수포인터 사용관련해서 질문을 남깁니다.
using SessionFactory = function<SessionRef(void)>; Service(ServiceType type, NetAddress address, IocpCoreRef core, SessionFactory factory, int32 maxSessionCount = 1); Service의 생성자는 이런식으로 SessionFactory라는 함수포인터를 받고 있습니다. 그런데 함수포인터를 전달하지 않고, ServerServiceRef service = MakeShared<ServerService>( NetAddress(L"127.0.0.1", 7777), MakeShared<IocpCore>(), MakeShared<GameSession>, // TODO : SessionManager 등 100); 이렇게 MakeShared로 생성된 GameSession 클래스를 전달해도 잘 동작하는데, 함수포인터 형식에 클래스를 그냥 사용해도 잘 동작하는 이유가 궁금합니다.MakeShared의 함수에서 ()를 사용하지 않으면, 내부적으로 xnew함수만 전달되어서 그런것인가요? 제가 이해한게 정확한지 모르겠어서 질문을 남깁니다. (한번도 function을 이렇게 사용한적이 없어서 모르겠네요 ㅜㅜ)
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
섹션4 네트워크 라이브러리 제작의 IOCPCore부분에 질문이 생겨 글을 남깁니다.
서버가 받은 클라이언트 소켓의 아이피와 포트를 출력하고 싶어서 Listner의 ProcessAccept함수 안의 출력부분에 코드를 이렇게 짰습니다.//..................... wstring IpAddress = session->GetAddress().GetIpAddress(); uint16 port = session->GetAddress().GetPort(); cout << "Client Connected!aaa" << endl; wcout << IpAddress << port<<endl; //........................그런데 출력이 계속 Client Connected! 라고만 뜹니다. 문자열을 아무리 변경해도 계속 이렇게 뜨네요. 포트문제인가 싶어서 컴퓨터를 껏다키고 해보아도 여전히 Client Connected!라고만 뜹니다. 이유가 무엇일까요?
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
클라이언트 연동 질문입니다
안녕하세요현재 해당 강의 수강중에 궁금한 점이 있어서 질문드립니다제가 4인이 한 세션에 들어갈 수 있는 게임을 만들고자 하는데 (유니티로 제작할 예정입니다) 유니티 클라이언트에 로비 레벨이 있고 각 클라는 로비 레벨에서 매칭 신청을 하면 c++서버에서 매칭 신청 클라를 데디서버 프로세스를 띄우고 해당 데디서버를 통해 세션플레이를 진행하고자 합니다제가 유니티를 안해봐서 유니티에도 언리얼 데디서버 같은 기능이 있는지 혹은 직접 데디서버 역할을 하는 c# 프로그램을 구현해야하는 것인지 궁금합니다.rookiss님 유니티 강의에서 다루는 내용이 해당 내용을 포함하는지도 궁금합니다
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
atomic<uint32> _popCount 관련
안녕하세요. 궁금한 게 있습니다._popCount에 관해 질문이 몇 개 보이는데 좀 다른 내용이지만 저도 관련해서 질문합니다._popCount 변수가 Pop 함수를 실행하는 쓰레드 개수를 추적하는 것인데요, Pop함수를 실행하는 쓰레드의 개수가 아닌, Node* oldHead = _head;이 코드에서 얻게 되는 동일한 포인터를 참조하는 쓰레드의 카운트를 추적해야 하는게 아닌가 하는 의문이 듭니다. 이를테면 Pop을 실행하는 쓰레드가 한 50개가 있다고 하면 계속해서 _popCount는 1이 될 수가 없을 거 같은데요, 실제로 테스트 해봤는데 Delete 함수로 진입을 안 합니다. 제가 잘 못 생각하는 부분이 있을까요?
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
공부 방향에 질문이 있습니다!
원래는 1년 전에 졸작을 만들기 위해 이 강좌를 참고하다가, 당시 수준으론 어려워서 대신 C# 강좌를 통해 유니티를 연동한 멀티플레이 VR 게임 졸작을 완성했습니다. 그러다가 이제 졸작 발표가 끝나고 현재 이 강좌를 보고 있는 중인데, 다만 오랜만에 찾아보니 [게임 프로그래머 입문 올인원]이라는게 있길래 같이 보는 중입니다. 그렇게 두 강좌를 같이 참고해서 보다 보니 이 강좌에서는[게임 프로그래머 입문 올인원] 에선 나오지 않는 여러 디테일한 내용들이 많은 걸 알 수 있었습니다. 일단 졸작에서 C# 서버를 만들어본 덕분인지 MSDN 문서를 참고하면 대충 강좌를 보지 않아도 서버 틀은 만들 수 있게 되었는데, 사실 이 강좌에서 나오는 디테일한 내용들은 여전히 머리가 빙빙 도는 상황입니다. 정확히 말하면 [게임 프로그래머 입문 올인원]의 서버는 어느정도 혼자 할 수 있을거 같은데,이 강좌에서 나오는 디테일한 내용을 혼자 채워넣으려고 하면 힘들다고 해야 할까요. 당장 데드락 사이클을 체크하는 내용만 봐도 알고리즘 공부를 다시 해야 한다는 걸 느끼는 중입니다. 원래 코테용으로 bfs나 dfs를 나름 공부하기는 했지만, 지금 지식으로는 저런 내용을 혼자 만드는 건 엄두가 나질 않습니다. 아무튼 감사하게도 일단 루키스님의 강좌가 있으니 지금은 이걸 보면서 공부하면 되는 것인데, 나중에 취업을 하면 강좌에 나오지 않은 다른 디테일한 내용들은 어떻게 공부를 해야 하는 걸까요? C# 강좌의 마지막에서 나오는 여러 기법들이나 해킹 관련 이슈의 대처법 같은 건 지금처럼 혼자 만든다고 터득할 수 있는게 아닐텐데 말입니다.아니면 취업후에도 따로 학원을 다녀야 하는 걸까요?만약 다닌다면 학원에서 어느정도의 내용을 배울 수 있는 건가요? 루키스님 강좌를 들어보면 중간에 서버 학원에 대한 간략한 언급들이 있던데 말입니다.일단 다음 학기를 마지막으로 졸업인지라, 이번에는 언리얼 포트폴리오 제작을 위해, 다음 강좌가 나오기 전까지 혼자 언리얼이랑 서버 연동을 도전해보는 것도 좋아보여서 해보는 중에 의문이 들어 질문드립니다.
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
페이지 질문
메모리를 페이지 단위로 관리하신다고 하셨는데VirtualAlloc을 통해서 int를 따로 2번을 요청하게 되면 위에 그림처럼 int가 연속적으로 배치되는게 아니라 페이지 단위만큼 떨어지게 메모리가 배치가 되는건가요??만약에 저렇게 배치가 된다면 size를 그대로 넣지 않고 직접 구해서 넣는 이유가 뭔가요??
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
Event Vs Condition_Variable
제목 그대로 Event와 Condition_variable의 차이가 단순히 Kernel 이냐 User Level이냐의 차이인지가 궁금합니다. CV에서는 조건을 추가해서 코드상으로 봤을 때, 깔금해지는 것은 알겠는데Event와 동일하게 Producer에서 Notify_one을 실행 하더라도 Consumer에서 바로 Lock을 잡지 못한다면 Producer가 한 번더 실행될 거같은데 이부분은 제가 이해를 못한건지 잘 모르겠습니다. 정리 -> cv를 이용해서 notify_one함수를 호출해도Producer에서 바로 Lock잡아버리는 상황이 발생하지 않나라는것. cv 장점 : 코드가 깔끔해지고, User_Level에서 동작한다. 다른것은 Event와 동일하다? 라고만 이해하면 되는지 궁금합니다.
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
안녕하세요 Client 를 WinAPI Project로 붙여보려고 하는데
Client의 생성된 Window창 x를 누르면 윈도우 창이 종료되지 않고 Client에서 굳이 Console창을 열어 마우스로 x를 눌러야지만 닫기는데 원인을 못찾겠습니다.. 혹시 짐작갈만한 원인이 있을까요?예상으론 Thread가 Join상태에서 끝나질 않아 발생하는 현상같은데 그럼 강제로 Thread로 생성해뒀던 무한Loop를 강제로 종료하는 방법을 작성해야할까요?
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
쓰레드매니저 질문
... void ThreadManager::Launch(function<void(void)> callback) { LockGuard guard(_lock); _threads.push_back(thread([=]() { InitTLS(); callback(); DestroyTLS(); })); } ... --------------------------------------------- int main() { for (int32 i = 0; i < 5; i++) { GThreadManager->Launch(ThreadMain); } GThreadManager->Join(); }쓰레드 매니저 예제 코드의 일부인데요, 위 코드에서 다음과 같이 InitTLS();GThreadManager->Join();두 곳에 브레이크 포인트를 걸었는데 신기하게 Join에 먼저 브레이크가 걸리네요. Launch 함수가 순차적으로 실행되고 메인함수의 반복문을 빠져 나온다음에 Join이 걸릴거 같은데요.Launch 함수가 쓰레드 함수라면 그럴 수 있겠지만 ThreadManager 자체는 쓰레드가 아닌데 왜 그런 것인가요?
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
안녕하세요. xdelete 관련 질문이 있습니다.
아래코드에서 xdelete에서 굳이 소멸자를 호출해줘야 하는 이유?가 궁금합니다.강의내용이 new, delete 함수를 재정의해서 사용하는거라서 명시적으로 xdelete를 사용하기 때문에 Knight 소멸자에 객체를 해제하는 코드가 없는것 같은데, 그렇다면 굳이 소멸자를 호출하지 않아도 되지않나요?만약 소멸자에 객체를 해제하는 코드를 구현해 놓는다면 사실상 free를 두번하는거지 않나 싶어서요. template<typename Type> void xdelete(Type* obj) { obj->~Type(); xrelease(obj); }
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
Reader-Writer Lock 질문
동일한 쓰레드 내에서 WriteLock을 잡은 상태에서 ReadLock도 잡을 수 있는 것은 이해를 했습니다.그래서 한 쓰레드가 WriteLock도 잡고 ReadLock도 잡은 상태에서 WriteLock를 통해 데이터 수정을 한다면 ReadLock에서는 수정이 되기 전에 데이터를 읽게 되는 것이 아닌가요??예를 들면, WriteLock에서 잡은 데이터가 1이고 그 후에 ReadLock을 잡으면 Read부분에서는 1에 데이터를 읽는데 이 상태에서 WriteLock에서 1에 데이터를 2로 수정을 한다면 ReadLock에서 잡은 데이터가 2로 수정이 안되지 않나요??
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
질문있습니다
if (_popCount == 1) { Node* node = _pendingList.exchange(nullptr); if (--_popCount) { DeleteNodes(node); } else if (node) { ChainPendingNodeList(node); } delete oldHead; }_popCount가 1인 상태가 나 혼자 삭제하고 있는 중이고 혼자 삭제하는 중이라면 삭제가 예약된 데이터들도 삭제한다고 이해를 했습니다. 삭제가 예약된 데이터들을 삭제를 할 수 있는지 체크하는 부분이 위에 있는 if(--popCount) 조건문으로 알고 있는데 여기서 --_popCount를 하면 _popCount가 0이 되어서 나 혼자 삭제하는 중이여도 다른 예약된 데이터들을 삭제를 할 수 없는거 아닌가요??
-
미해결[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
Cmake 에서 Generate 할때 CMakeLists.txt 파일이 없다는 Error는 어떻게 해결할 수 있나요??
이렇게 뜨는데 해결방법을 모르겠습니다 ㅠㅠ그리고버전을 23버전으로 사용했는데공부하는 시점에서 강의에 나오는 3.17로 진행하는건 문제가 없을까요??
-
해결됨[C++과 언리얼로 만드는 MMORPG 게임 개발 시리즈] Part4: 게임 서버
포폴용 iocp서버를 배포 하고 싶습니다
포폴용 게임 서버 구성을 위 처럼 하고 싶은데, windows인 IOCP서버 배포에 관해서는 정보가 없어서 가이드를 받고 싶습니다. 게임에 대해 좀 더 구체적으로 말씀드리면회원가입/로그인 등 실시간성이 중요하지 않은 컨텐츠들은 ASP.Net으로 로비동작들을 구현하고실시간 성이 중요한 배구는 IOCP 서버로 소켓 연결해서 게임을 구현하고자 합니다. 위와 같은 구조로 게임 서버를 AWS에서 배포를 한다면 각 asp.net, redis, mysql, windows별로 EC2해서 배포 하는거 말곤 답이 없을까요...?혹시나, 도커를 쓸 수 있다면 혹시 가능하다면 말씀해주시면 감사하겠습니다.🙇♂️