336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\TCPIP\Parameters 


에 REG_DWORD 타입으로 MaxUserPort 를 추가하고 60000 이라고 입력하면 이론상 60000까지 됩니다.


출처 : http://www.gpgstudy.com/forum/viewtopic.php?p=84282

'Programming > Network' 카테고리의 다른 글

FTP Active 모드와 Passive 모드  (0) 2015.07.21
DNS(도메인 네임 서버) 초기화 하는 방법  (0) 2015.02.28
Dead Reckoning  (0) 2015.02.07
NAT (Network Address Translation)  (0) 2015.02.07
공인 IP / 사설 IP  (0) 2015.02.07
Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

네트웍 게임을 개발할때 부딪히는 물리적 한계가 두가지 있습니다.

Bandwidth 와 Latency

Bandwidth의 한계로 신호를 많이 보낼 수 없는 것 뿐만아니라, 자주 보낼 수도 없습니다.

기본적으로 리얼타임게임에서는 매 프레임 마다 상태 정보를 갱신해야 합니다. 
만약 30FPS 정도의 갱신률을 가진 게임을 네트웍 플레이로 만든다면 1초에 30번 플레이어의 상태정보를 전송해야합니다.
전송만 하는게 아니라.. 다른 플레이어들의 정보도 전송 받아야 하지요.
이렇게 하면 아무리 넉넉한 Bandwidth를 가졌다 해도 플레이어의 숫자가 늘어남에 따라 금방 Bandwidth가 차 버립니다.

네명정도를 최대 플레이어 수로 제한 한다면 모르지만 제한된 Bandwidth 내에서 많은 수의 동시 플레이어를 지원하려면 우선 매프레임 마다 정보를 보내는 걸 포기해야합니다.

그런데 게임은 기본적으로 매프레임 마다 전체 상태를 갱신해야 하는데, 이걸 매프레임 마다 보내지 않는 다면 정보가 전달되지 않는 프레임 동안에는 어떻게 하지요??

이때 사용되는 기법이 바로 Dead Reckoning 입니다.
Dead라는 말은 신호를 받지 못하고 있는 상태를 말합니다.
즉 신호가 전달 되지 않으니 신호가 죽은셈이죠. 
Reckoning은 추산하다는 뜻으로 신호가 없는 동안에도 추측으로 계산한다는 겁니다.

다시말해서 신호가 없는 동안에도 이전에 받았던 신호를 바탕으로 추산해서 상태정보를 갱신한다는 겁니다.

Dead Reckoning은 주로 플레이어의 위치정보를 갱신하는데 사용됩니다. 
물론 데드 레커닝 없이 매 프레임마다 플레이어의 위치값을 주고 받을 수 있으면 좋지만.. 제한된 Bandwidth 때문에 그렇게 할 수가 없지요.

그렇다면 플레이어의 정보를 전달할때 현재의 위치 값 뿐만아니라 위치 값이 전달되지 않는 동안에도 위치 값을 추측하는데 데 필요한 부가적인 정보를 같이 보내야 합니다.

이런 정보는 보통 속도나 가속도 값이 됩니다. 
물론 속도만 보낼 수도 있고, 가속도 까지 보낼 수도 있습니다. 
경우에 따라서는 위치값만 보내더라도 이전 위치 값을 기초로 속도를 구해서 처리 할 수 도 있습니다.

고등학교때 배운 물리공식을 상기하면..

X = X0 + V * t + 1/2 * A * t * t
(X :위치, V :속도, A :가속도, t :시간)

최근에 받은 위치값과 속도, 가속도를 이용해서 쉽게 이후 시간의 위치를 추측할 수 있죠.

물론 이 값은 어디까지나 추측일 뿐이고 신호가 없는 동안에 일반적으로 운동상태가 바뀌어졌겠죠. 
이럴 경우 다음 신호가 전달 되어 왔을때 추측한 값이랑 비교해보면 서로 다르겠지요. 
차이가 별로 없다면 추측한 값은 버리고 새로 받은 위치정보로 갱신해버리면 족하지만... 그렇지 않은 경우 새로받은 위치정보로 갱신해버리면 워프하듯이 갑자기 위치가 바뀌어 버리고 어색하게 보일 겁니다.
우리가 네트웍 게임을 하다보면 흔히 목격하는 광경이죠.

이런 경우 바로 갱신하지 말고 새로받은 위치 정보로 새로운 추측을 해서 현재의 추측값에서 새로운 추측값으로 부드럽게 연결할 수도 있습니다. 
이러면 겉보기 결과는 좀 더 나아지겠지만 공짜로 되는 건 아니지요. 
부가적인 계산이 더 추가되겠지요. 
CPU타임이 남아 돈다면 모르지만 그렇지 않다면 그냥 워프되는걸 감수 해야지요.
이처럼 신호가 없는 동안에 간단한 물리공식을 이용해서 위치값을 추정 할 수는 있는데..

그러면 다음 문제는 신호를 얼만큼 덜 보낼 것인가이죠. 
예컨데 30FPS 의 게임의 경우 매 5프레임 마다 보낼 수도 있고 10프레임 마다 보낼 수도 있고, 15프레임 마다 보낼 수도 있고, 혹은 1초에 한번만 보낼 수도 있지요. 
이건 사실 정답이 없지요. 
게임이나 네트웍 등의 상태에 따라 다르겠죠.

일률적으로 몇 프레임 마다 보내는 방법 외에.. 필요할때만 보내는 방법도 생각할 수 있습니다. 
이런 경우는 서버에서도 데드 레커닝을 해야하지만..
각 클라이언트에서 날아오는 플레이어 위치정보를 그때 그때 다른 클라이언트로 전달하는 대신 서버도 나름대로 클라이언트와 똑 같은 방식으로 데드래커닝을 하고 있다가 받은 정보가 추측한 값이랑 적정한 문턱값 이상으로 차이가 발생했을때만 다른 클라이언트에 보내는 겁니다.

실제적인 적용에 있어서는 여러가지 다양한 방법을 생각해 볼 수 있겠지요.

다음의 문제는 latency가 되는데 여태까지의 논의는 어디까지나 latency 가 없다는 전제하에서 그런 것이고, latency까지 고려한다면 문제는 좀 더 복잡해 집니다.

보통 실용적인 견지에서 동일한 LAN상에서라면 latency를 무시해도 무방하지만 인터넷을 통해서 접속을 하게 되면 이제는 latency를 무시 할 수 없게 됩니다.
미국처럼 대양을 건너 다른 대륙까지 연결되는 경우가 아닌 국내에서 서로 접속한다고 해도 latency는 심각하게 고려해야 합니다.

물론 바둑이나 장기처럼 Turn 방식으로 진행되는 게임들에는 전혀 상관 없는 얘기 것지만...^^;

latency 문제는 다음에...

 

 

네트웍 게임을 개발하면서 많은 경우 간과 되고 있는 부분이 Latency를 어떻게 처리 할 것인가 입니다.

대개 Bandwidth(대역폭)에 대해서는 인지하고 있는데...
Lantency의 경우는 근본적인 원인을 알지못하고, Modem 이라서 느리다는 식으로 이해하는게 보통이죠.

Lantency는 우리말로 번역한다면 신호지연 이라고 할 수 있습니다. 
네트웍의 한 노드에서 다른 노드로 신호가 전달되는데 시간지연이 생긴다고 이해하시면됩니다.

구체적인 데이타의 형태가 어떠하던 결국 네트웍을 타고 전달되는 신호는 전자기신호입니다. 
단순히 전기신호일 수도 있고, 광케이블인 경우는 빛 신호가 될것이고, 인공위성이라면 전자기파 신호이겠죠. 
빛도 전자기파의 한종류이므로 결국은 모두 전자기 신호이죠.

그런데 아인슈타인의 특수상대성이론에 의하면 물리적으로 가장 빠른 속도는 빛의 속도입니다.
정보의 전달도 마찬가지로 빛의 속도가 최대치입니다.
이보다 더 빨리 전달될 수는 없습니다.
(적어도 아인슈타인의 상대성이론을 능가하는 이론이 나오기 까지는...)

일반적인 네트웍 어플리케이션에서는 이러한 정보전달 속도의 한계가 전혀 문제 될 게 없습니다.
주로 대역폭이 문제가 되지요.
하지만 리얼타임으로 상호작용해야 하는 게임의 경우는 중요한 문제가 됩니다. 
혹자들은 네트웍상에서 정보는 결국 전자기신호로 전달되므로 빛의 속도로 전달될 것이고, 빛의 속도는 엄청빠르기 때문에 문제될게 없다고 생각할 수도 있습니다.

하지만 바로 이 빛의 속도라는 한계가 문제가 됩니다.
초속 3십만킬로미터 라는 어마어마한 빠르기의 빛의 속도라고 해도 리얼타임 게임을 하기에는 느립니다.

같은 게임방내에서 랜으로 접속된 컴퓨터 들 사이라면 무시해도 되지만 인터넷을 통 해 미국에 있는 컴퓨터와 통신을 한다면 문제가 됩니다.

간단하게 계산을 해보지요.
흔히들 알고 있기로 빛이 1초에 지구를 7바퀴 반을 돌 정도의 속도라고 알고 있습니다.
계산을 편하게 하기 위해서 이것보다는 조금 빠른 1초에 열바퀴도는 속도라고 합시다.
그렇다면 지구를 한바퀴도는데는 약 1/10초가 걸립니다. 
그러니까 100밀리세컨드죠.
미국이라면 우리나라를 기준으로 대충 지구 반대편에 있으므로 반바퀴 정도라고 보면 됩니다. 
그러면 미국까지 가는데는 대략 50밀리세컨드가 소요됩니다. 
1/20초이죠.

게임 프로그램은 보통 프레임 단위로 모든 걸 처리하므로 FPS가 30인 게임이 있다면 1/30초 안에 모든 작업을 완료해야 합니다.
그런데 미국까지 신호가 가는데만도 1/20초가 걸리니 게임프로그램이 한 프레임을 갱신하는데 주어진 시간보다 더 느립니다.

흔히들 네트웍 게임을 하면 Ping 이니 lag이니 해서 Ping값이 높은 모뎀은 나가라고 들 하지요.

하지만 제아무리 기가급의 초초고속 인터넷망에 물려있다해도 물리적인 제한을 넘을 수는 없습니다. 
미국까지 ping하면 패킷이 미국까지 갔다 와야하므로 최소한 1/10초는 걸립니다.
흔히들 대역폭이 커다는 걸 네트웍의 속도가 빠른 걸로 표현하니까 신호가 전달되는데 걸리는 시간이 빠른 것과 혼돈을 하는데, 대역폭은 어디까지나 단위시간당 전달되는 데이타의 양이지 결코 신호가 전달되는 속도를 말하는게 아닙니다.

물론 지금까지 따져본 것은 신호전달의 물리적 한계인 빛의 속도만 고려한 겁니다. 
하지만 인터넷 상에서 실제로 신호가 전달되려면 여러개의 라우터를 거쳐서 지정된 주소의 컴퓨터로 전달됩니다. 
라우터가 신호를 받으면 즉시 전달하는게 아니라.. 버퍼에 대기시켰다가 어디로 가는 신호인지 구분해서 보내게 되므로 라우터가 신호를 처리하는데 걸리는 시간까지 포함시켜야지요.
세밀하게 따진다면 컴퓨터에 달린 네트웍카드에서 부터 벌써 하드웨어적인 지연이 생기죠.
프로그램이 데이타전송을 네트웍카드에 요청하면 즉시 신호가 전달되는게 아니라 네트웍 카드내의 버퍼에 잠시라도 대기했다가 라인이 비면 보내집니다.

이런식으로 따지면 신호가 미국까지 가는데 더 많은 시간이 걸립니다.

실제로 미국에있는 서버를 선택해서 Ping을 때려보면 알 수 있습니다. 
절대로 100밀리세컨드 이하로는 나오지 않습니다.
혹시라도 나오면 노벨물리학상을 탈 수 있을지도..
신호가 빛보다 빨리 전달되는 걸 발견했으니.. 대단한 과학적 발견입니다.^^;

결론적으로 이러한 네트웍의 latency 는 결코 줄일 수 없는 물리적인 한계입니다. 
그래서 인터넷상에서 이루어지는 게임의 경우 이러한 latency를 어떻게 잘 처리하는 냐가 중요한 문제가 됩니다.
더군다나 이러한 latency가 물리적인 신호전달속도에만 의해서 발생하는게 아니라 라우터를 거치면서도 발생하기 때문에.. 값이 고정되어 있지도 않습니다.

그러니까 퀘이크나 언리얼 같은 게임은 3차원 엔진으로만 대단한게 아니라.. 대역폭은 제껴놓고라도 lantency를 극복하고 인터넷상에서 네트웍 플레이가 가능하게 한 것만으로도 대단한 겁니다.

< ps >
latency 를 극복한다는 건 latency를 없앤다는 뜻이 아니라....
(이건 결코 없앨수가 없지요. 빛보다 빠를 수는 없으니..) 
latency가 존재함에도 불구하고 게임 플레이가 가능하게 한다는 뜻이죠... 
물론 ping값이 300ms 를 넘어가기 시작하면 백약이 무효이긴 하지만....
실용적인 견지에서 300ms 이하에서는 latency를 잘 감추어서 플레이하는 플레이어들은 눈치 못채게 해야지요..
이게 결코 쉬운게 아니라는 거지요.. 
사실 150ms가 넘어가면 플레이어가 눈치 못채게 하기는 정말 힘듭니다.


Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

요약 : 사설 IP주소를 공인 IP주소로 바꿔주는데 사용하는 통신망의 주소 변환기이다.

 

본문 :

NAT를 사용하는 목적에는 2가지가 있는데, 첫째는 인터넷의 공인 IP주소를 절약할 수 있다는 점이고 둘째는 인터넷이란 공공망과 연결되는 사용자들의 고유한 사설망을 침입자들로부터 보호할 수 있다는 점이다.

인터넷의 공인 IP주소는 한정되어 있기 때문에 가급적 이를 공유할 수 있도록 하는 것이 필요한데 NAT를 이용하면 사설 IP주소를 사용하면서 이를 공인 IP주소와 상호변환할 수 있도록 하여 공인 IP주소를 다수가 함께 사용할 수 있도록 함으로써 이를 절약할 수 있는 것이다.

공개된 인터넷과 사설망 사이에 방화벽(Firewall)을 설치하여 외부 공격으로부터 사용자의 통신망을 보호하는 기본적인 수단으로 활용할 수 있다. 이때 외부 통신망 즉 인터넷망과 연결하는 장비인 라우터에 NAT를 설정할 경우 라우터는 자신에게 할당된 공인 IP주소만 외부로 알려지게 하고, 내부에서는 사설 IP주소만 사용하도록 하여 필요시에 이를 서로 변환시켜 준다. 따라서 외부 침입자가 공격하기 위해서는 사설망의 내부 사설 IP주소를 알아야 하기 때문에 공격이 불가능해지므로 내부 네트워크를 보호할 수 있다.


출처 : http://100.naver.com/100.nhn?docid=717874

Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

공인 IP는 말그대로 외부에 공개가 되어있는 IP입니다. 때문에 각 호스트당 한개밖에 사용을 할수 없다고 하죠

이 말인즉슨 외부에는 공인IP를 찾아가기 위한 라우팅 경로가 항상 존재합니다. 때문에 제가 공인IP를 사용하고 있다고 하면 다른곳에서도 라우팅 경로를 통해 내 PC에 접속을 할수가 있죠. 그리고 제가 공인IP를 PC에 설정하고 사용한다고 하면 네이버에 접속한다고 할때 네이버까지 패킷이 도달했다가 다시 되돌아 와야 하는데 공인IP를 사용하기 때문에 라우팅 경로를 보고 제 PC를 다시 되찾아 올수가 있는 겁니다.

 

하지만 사설IP는 외부에 공개가 되지 않은 IP입니다. 이말은 외부에 라우팅 경로가 존재하지 않는다고 생각하시면 되십니다. 때문에 제가 사설IP를 사용하면서 외부로 인터넷을 할수 없는건 외부로 데이터가 나가지만 이 패킷이 되돌아올때는 라우팅 경로를 보고 찾아오는데 사설IP는 라우팅 경로가 존재하지 않으므로 출발지 IP까지 찾아오질 못합니다.(각각 라우터 사이에 시리얼 구간을 사설IP로 셋팅을 하는 경우도 있긴 있습니다.)

 

IPv4에서는 사설IP를 정해서 사용하고 있습니다. Class A는 10.0.0.0 ~ 10.255.255.255까지 이며 Class B는 172.16.0.0 ~ 172.31.255.255이며 Class C는 192.168.0.0 ~ 192.168.255.255입니다.

 

그럼 내부에서 사설IP를 사용중인데 인터넷이 되는건 무슨 이유일까요?

NAT라는 설정을 통해 가능합니다. 예를 들어 업체에서 VDSL을 사용하고 있다고 합니다. 각 인터넷 회선당 공인IP는 보통 한개가 부여가 되죠. 업체 내부에서는 사설IP를 사용하고 있다고 합니다. 만약 공유기나 기타 다른 GW장비를 사용하신다고 하면 내부에서 사용하는 사설IP는 외부로 나갈때는 NAT를 통해 인터넷 회선이 사용중인 IP로 매핑이 되서 나갑니다. (매핑이라는 표현보다는 NAT라는 표현이 더 낫겠지요.) NAT라는건 IP를 변환시켜주는 것을 의미합니다. NAT에서도 여러가지 방법이 있지만 지금같은 경우는 SNAT 또는 PNAT라고 하겠지요

즉, 업체에서 192.168.1.0/24 대역을 사용하고 있다고 합시다. 이건 사설IP이죠. VDSL에서 받아온 IP는 203.84.255.5라고 합니다. 그럼 내부에서 사용하는 사설IP들이 외부로 인터넷을 할때는 사내에 설치된 GW장비를 거치면서 VDSL에서 받아온 공인IP로 NAT되어 나간다는 겁니다. 외부로 데이터가 갔다가 VDSL까지는 공인IP이기 때문에 다시 되돌아 올수있겠죠, 그럼 GW장비에서는 그데이터를 받을거고 내부에서 사용중인 사설IP에 대한 라우팅 정보를 가지고 있으므로 패킷을 내부로 되돌려 줄수가 있겠죠 이렇게 해서 통신이 되는겁니다.

 

NAT가 IP를 변환하는건데 어떻게 많은 사설IP들이 IP하나로 나가도 문제가 없는건가요?

통신을 할때 포트를 사용하지 않습니까? TCP나 UDP포트를 사용하죠. 이 포트에도 여러가지 규칙을 정해놓았습니다. 예를들어 일반적으로 사용하는 FTP는 21번포트, HTTP는 tcp 80번포트등등 모두 정해놓았죠. 하지만 출발지에서 나가는 포트는 어떠한 포트를 나가더라도 상관이 없습니다. 목적지에 도달하는 포트만 정확하면 상관없죠. 예를들어 내부에서 http를 통해 네이버에 접속한다고 칩시다. 그럼 네이버에 접속할 포트는 tcp 80이 되겠지만 출발할때 포트는 1번이 될지 99번이 될지 4324가 될지 모른다는거죠. 하지만 상관이 없다는 겁니다. 목적지 포트만 확실하면 되는거니까요. GW장비에서 패킷을 확인해보면 내부 사설IP에서 출발하는 포트는 여러군데입니다. 하지만 목적지로 가는 포트들은 모두 80으로 확인이 되실거에요


출처 : http://cafe.naver.com/neteg/66261

Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

1. 소켓 이벤트 핸들링

 

IOCP > Overlapped Callback > select > WSAAyncSelect > WSAEventSelect

순서로 좋다고 합니다.

 

제 기억으로 2003년까지만 하더라도 IOCP 방식의 유용성에 대한 논란이 있었지만 이후 Windows 에서 대용량 서버를 만들 때 당연히 사용하는 방식이 되었습니다.

 

책에서 보니 1000명 이하에서는 select 방식도 성능이 괜찮았습니다. 1000명 이하의 접속을 처리할 때는 단순한 개발 및 멀티 플랫폼 대응을 위해 select 방식을 사용하는 것이 좋겠습니다.

 

WSAAyncSelect는 제 생각보다 성능이 좋지 않더군요. WSAEventSelect 보다 성능이 더 좋지 못하지만 WSAEventSelect는 성능도 괜찮고 사용 방법도 간편한데 접속이 64개밖에 되지 못하는 단점이 있습니다.

온라인 게임에서 클라이언트 측 소켓은 WSAEventSelect 방식을 사용하는 것이 좋겠습니다.

 

 

 

2. Accept 방식

 

AcceptEx + Pooling 이 제일 좋다고 합니다.

그렇지만 단순하게 접속 성능 테스트에서는 AcceptEx + No Pooling과 별 차이가 없지만 Pooling을 하면 Accept 부분을 빨리 처리할 수 있기 때문에 TimeOut 발생 확률을 줄일 수 있다고 합니다.

 

WSAAccept + Loop는 접속 처리 성능은 좋으나 동시 접속 수가 많을 때 TimeOut이 발생할 확률이 높다고 합니다.

 

 

 

3. 데이터베이스 인터페이스

 

작년까지만 하더라도 이 부분에서 제가 착각하고 있었던 것이 OLEDB가 ODBC 보다 빠를 것이라고 생각했는데 그렇지 않고 반대라는 것을 알게 되었습니다.

가볍고 속도를 중시할 때는 ODBC 방식이 좋고, ADO는 사용은 편하지만 성능상으로는 ODBC, OLEDB, ADO 중 가장 좋지 못합니다.

 

 

 

4. Nagle

 

수치적으로 No Nagle이 더 좋게 나오지만 사용하는 환경에 따라 꼭 좋다고만 할 수 없을 것 같습니다.




출처 : http://cafe.naver.com/jzsdn/16156

'Programming > Network' 카테고리의 다른 글

NAT (Network Address Translation)  (0) 2015.02.07
공인 IP / 사설 IP  (0) 2015.02.07
최적의 스레드 수를 찾기 위한 시작점  (0) 2015.02.07
OSI 7 Layer & TCP/IP 4 Layer  (0) 2015.02.07
Nagle Algorithm  (0) 2015.02.07
Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

SYSTEM_INFO lpSystemInfo;

 

GetSystemInfolpSystemInfo );

 

lpSystemInfo.dwNumberOfProcessors * 2 + 2

 

이 숫자가 적당하다는 얘기지 최적이란 얘기는 아니다!

'Programming > Network' 카테고리의 다른 글

공인 IP / 사설 IP  (0) 2015.02.07
"온라인 게임서버 프로그래밍 벤치마크" 초간단 정리  (0) 2015.02.07
OSI 7 Layer & TCP/IP 4 Layer  (0) 2015.02.07
Nagle Algorithm  (0) 2015.02.07
서버 프로그래밍시 주의점  (0) 2015.02.07
Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.


Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

Nagle 알고리즘을 요약하자면 다음과 같다. 

 

ACK를 받지 못한 데이터가 있는 상황에서는, 조그만 세그먼트들은 ACK를 받을 때까지 보낼 수 없다.  
대신 이 조그만 세그먼트들은 하나로 합쳐져서 ACK가 도착했을 때 하나로 날아가게 된다. 

  

 ACK가 빨리 올수록 데이터도 빨리 날아간다. 하지만 ACK가 바로바로 날아오지 않는 상황(즉 느린 WAN)에서는 알고리즘을 적용하지 않았을 때보다, 더 적은 수의 세그먼트들이 날아가게 된다. 즉 병목 현상을 줄이는 데 도움이 된다. 하지만 결국 데이터를 모아서 보내는 것이기 때문에 원래보다 반응이 느려진다. 빠른 반응이 필요한 애플리케이션의 경우, 이 알고리즘을 사용하지 않는 것이 도움이 될 수 있다.

 TCP_NODELAY 소켓 옵션을 이용해 알고리즘을 끌 수 있다.


출처 : http://www.serious-code.net/moin.cgi/TcpGlossary

Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

* strcpy 등의 길이제한이 없는 함수는 사용하지 않는다

-> strncpy, memcpy와 같은 함수를 사용하고스트링 맨 끝에, 0을 넣어주는 것이 안전하다특히나 클라이언트에서 올라온 데이터는 더더욱 그렇다.

 

포인터 검사는 반드시 하라

-> 포인터 사용시에는 무조건 NULL포인터 검사를 하는 것이 좋다바로 쓰고 싶을 경우는 레퍼런스를 사용해서 항상 유효한 데이터임을 알린다.

 

로그는 규격을 정해서 만들자

-> 로그는 분석이 필요하기 때문에로그 분석기를 적용하기 쉽도록 규격을 정해서 만들자.

 

서식 지정자에 넣는 값에 유의하라.

-> 스트링 안에 %s %d 라는 코드가 있고가변 인자가 주어지지 않으면 에러가 발생한다.
%s 
로 문자열을 입력 받으려 하는데, float형이나, int형을 입력했을 때에도 C는 널을 만나기 전까지 데이터 읽는 것을 멈추지 않는다잘못된 메모리를 접근 문제는 언제나 조심하자

 

돈은 signed 형을 사용한다.

-> unsigned 형을 썼다가 자칫 뺄셈을 잘못할 경우 몇 십억이 되는 돈이 들어 갈수가 있다.

 

클라이언트에서 받은 값은 유효한 값인지 검사 한다.

-> 어떤 값이 들어올지 모른다신용은 금물!

 

아이템 장착 해제 시에는해당 아이템이 장착 중인지를 반드시 검사한다!

-> 클라이언트가 중복 착용/해제 시도를 안 할거라는 확신을 하지 말아라확신은 서버에서 직접 검사를 한 후에 해라.

 

검사 시점을 주의하라

-> 즉시 이뤄지는 처리가 아닌다른 곳에서 인증이나 처리를 하고 온 후 처리 되는 경우라면민감해야 한다.

다른 곳으로 처리를 하러 간 도중에이 값을 어떤 식으로든 사용하게 된다면오류가 생기기 때문이다.

 

테스트는 최대한 실 서버와 같은 환경에서

-> 가급적이면 서버는 테스트 코드를 적게 돌려야 한다. QA와 같은 테스트는 실 서버와 같은 환경에서 이뤄져야 실 서버 패치 후또는 실 서버 패치 시에 생기는 문제를 방지할 수 있다또한 환경 파일 (cfg, ini를 비롯한 데이터 파일)의 무결성 검사도 반드시 하도록 하자.

 

추가 하는 코드에 대해 명확히 이해하라

-> 코드를 추가할 때그 코드가 어떤 기능을 하는지 간단한 테스트라도 해라처음 시도사용하는 알고리즘이나 라이브러리 사용시에는 특히 주의하라그 기능을 명확히 이해하지 못하고 사용한다면그 것은 우연에 맡기는 프로그래밍을 하는 것이다.

 

적은 조건을 만족해도 잘 돌아가는 코드를 작성해라 (복잡도를 줄여라)

-> 많은 조건을 충족 해야 하는 상황에서만 잘 돌아가는 코드보다는적은 조건을 만족하는 상황에서도 잘 돌아가는 코드가 좋은 코드다특별한 이유(속도 향상메모리 제약 등)가 없다면 유연한 코드를 작성해라.

 

가정을 하지 마라코드에서 직접 제약을 걸어라.

-> 어떤 처리에 대한 클라이언트와의 규약 (예를 들면비번 방 지정은 방장만 할 수 있다던가게임 방에서만 가능하다던가 하는 가정)은 반드시 지켜질 수 있도록 코드에서 그 동작이 불가능 하도록 만들어라.

재귀적인 동작을 조심해라

재귀적으로 돌다 스택 오버 플로우가 나는 상황이나처리 과정이 맞물리다 재귀적으로 처리가 이뤄져 사용하는 메모리를 잃어 버리는 경우를 조심하라재귀로 인한 스택 오버 플로우는 말 할 필요도 없고재귀적으로 처리가 이뤄지다가 클래스 안이나힙에 잡힌 메모리의 주소를 사용하는 경우 프로그램의 비정상 동작이 원인이 될 수 있다혹시나 재귀적으로 돌아갈 여지가 생긴 경우에는 반드시 지역 변수로 선언해서 스택에 할당한 메모리를 사용하라.

 

멀티 쓰레드 시 동기화는 주의 깊게 하라

멀티 쓰레드에서 같은 데이터를 동시에 접근하지 못하도록 동기화는 필수다이 작업은 수작업이 덜 필요하도록 상위 단에서 작업 하는 것이 중요하다.

 

시간차에 주의하라

DB처리가 실 시간이 아닌 경우에는, (큐에 담아두었다 처리 하는 경우시간차가 있다이 시간차에 주의하자서버가 여러 대인 경우다른 서버로 처리하러 떠난 상태까지 고려하도록 하자.

포인터를 담는 자료구조에서해당 자료를 빼고포인터에 동작할당 된 주소를 delete할 때 주의하라

한 곳에서 new한 데이터를여러 곳에서 사용할 때 주의하라. new한 객체의 delete는 가급적 한 곳에서만 하라. delete된 포인터를 자료구조에서 들고 있으면 dangerous 포인터가 되니 조심하자.

코드 재 사용시 가정이 깨지는 것에 주의하라

같은 코드를 다른 곳에서 재 사용시에 기존에 수립한 가정을 다시 검토하라.


배열 접근 시에는 무조건 범위 검사를 하라

배열 접근 인덱스는 반드시 유효한 값인지 범위 검사를 하라가급적이면 배열 접근 인덱스는 unsigned 한 값으로 사용해서배열 검사를 한번에 끝내는 것이 좋다.

자료구조에서 넣는 키 값과빼는 키 값에 주의하라.

온라인 서버 게임에서 호환을 위해 대소문자 캐릭터 아이디를 모두 메모리에 들고 있는 경우가 있다이 때 자료구조에 소문자 캐릭터 아이디로 넣고대문자 캐릭터 아이디로 빼는 경우문제가 생겼다주의 하자.

로그를 실서버개발 서버에 따라 다르게 동작시키자.
QA개발 서버 때 찍을 로그와 실 서버에서도 찍을 로그를 구분하고쉽게 변경 가능하도록 하자. (개발자 명령어 등을 통해서서버가 러닝중인 상태에서도 해당 변수 플래그를 바꿔 로그를 찍거나 찍지 않도록 만들자)

 

증명을 하자
프로그래머는 추론이 아닌 증명을 해야 한다특정 상황이 의심스럽다면 그 상황이 맞는지 입증해라.

성급한 일반화의 오류를 범하지 말자
특정 플랫폼특정 컴파일러특정 라이브러리의 구현이 일반적이라고 믿는 일반화의 오류를 범하지 말자구현은 천차만별이다.

실 서비스에 적용할 바이너리에 대한 점검은 신중히 하자.

실 서비스에 적용될 변동 사항은 한번 더 생각하고한번 더 테스트해보자그리고일어날 수 있는 파급효과를 꼼꼼히 따져보자.


* DB
스키마쿼리는 반드시 튜닝하자

쿼리 프로파일러 등을 통해서 DB 부하를 측정하라쿼리 자체가 느리다면쿼리 호출 횟수가 작아도 문제가 생길 수 있다.

* DB 접근 횟수를 조절하자
서버가 크리티컬한 이유에 DB는 절대 빠지지 않는다. DB는 데이터 저장소로써 매우 중요한 의미를 가지는데, DB 테이블 설계와쿼리로 인한 파급효과를 예측하는 것은 여러모로 중요하다하지만, DB에서 아무리 쿼리 튜닝스키마 최적화를 한다 해도코드에서 지나치게 많은 쿼리 호출비정상적으로 많은 데이터 삽입 등을 해서데이터 량 자체가 많다면 그 효과를 보기 힘들 것이다. DB사용량에 대한 코드에서의 최적화가 최 우선적으로 이루어지도록 하자.


출처 : http://blog.naver.com/elky84/10013134784

Posted by 역시인생한방
,
336x280(권장), 300x250(권장), 250x250, 200x200 크기의 광고 코드만 넣을 수 있습니다.

디버깅할때 아래와 같은 한줄을 추가하면

 

int x = WSAGetLastError();

 

가장 최근에 일어난 윈속에러를 변수 x 를 통해 알 수 있다.

 

x 에 대입된 값을 MSDN 이나 컴파일러의 Error Lookup 에 입력해서 원인을 파악할 수 있다.

Posted by 역시인생한방
,