[2014 CodeEngn Conference 10] 노용환 - 디버거 개발, 삽질기GangSeok Lee
2014 CodeEngn Conference 10
MS 에게 속았어요
Windows 운영체제가 지원하는 디버거 지원 기능들과 브랜치 트레이서를 구현하기 위한 몇 가지 방법들을 소개하고, Windows 커널에 이미 구현되어있는 하드웨어 기반 브랜치 트레이서 코드 분석과 여기에 존재하는 의도된(?) 버그를 살펴본다.
http://codeengn.com/conference/10
http://codeengn.com/conference/archive
[2014 CodeEngn Conference 11] 박한범 - 가상화 기술과 보안GangSeok Lee
2014 CodeEngn Conference 11
가상화와 보안의 합작
가상화 기술은 대상체를 추상화된 리소스로 가상화하여 활용할 수 있는 기술이다. 가상화 기술이 하드웨어 차원에서 지원되기 시작한 이후로 CPU가 제어하는 자원을 하드웨어 레벨에서 가상화 할 수 있게 되었다. CPU가 하드웨어 수준에서 가상화를 지원하기 위해 설계된 구조와 인터페이스가 존재하는 계층이 기존에 운영체제에서 사용하던 Ring 0~3 계층 상위에 추가되면서 이를 보안에서 활용하는 시도들이 있어왔으며 대표적으로 ARM TrustZone 아키텍처가 있다. TrustZone과 같은 아키텍처는 운영체제와는 다르게 오직 보안에 관련된 서비스와 기능만을 탑재한 보안전용운영체제를 먼저 상주시킨다. 운영체제가 특권/사용자 계층을 나누어 사용자 계층에서 하드웨어 자원에 접근하는 것을 막고 대신 요청을 받아 처리함으로서 하드웨어 자원을 보호했던 것과 유사하게 보안/일반 계층으로 나눠 보안이 필요한 동작시에 보안전용운영체제가 요청을 받아 처리하는 구조를 갖고, 일반 계층은 격리되어 보안 계층에 접근할 수 없으므로 보안성을 한층 높힌 구조이다. 본 발표는 가상화 기술에 대한 개괄적 설명과 이를 활용한 PS/2 키로거를 제작 I/O를 가로채는 과정을 살펴보고 운영체제 상위 권한이 어떤 의미를 갖는지 그리고 CPU하드웨어 레벨의 강력한 권한을 체험하는 것을 통해 가상화 기술의 특성을 파악해보자 한다.
http://codeengn.com/conference/11
http://codeengn.com/conference/archive
본 발표자료에서는 이더리움 플랫폼의 상세 아키텍쳐와 기반 기술, 그리고 스마트 컨트랙과 이를 기반한 Dapp의 개발 방안에 대해 소개한다. 이더리움은 블록체인 기반 기술하에 암호 화폐의 생성 , 전송 등 라이프사이클 관리외에 스마트 컨트랙을 지원한다. 스마트컨트랙은 서로 모르는 당사자간의 계약을 준수하도록 강제할 수 있는 응용 프로그램이다. 컨트랙 프로그램은 바이트코드로 컴파일된 후 블록체인을 통해 배포되고 , 로컬 로드상에서 실행되는 일종의 에이전트라 볼 수 있다. 이렇게 개바된 스마트컨트랙은 기존 웹 인터페이스를 통해 접근하고 활용할 수 있으며 이렇게 스마트 컨트랙 기반하에 개발된 응용 서비스를 Dapp이라 한다.
[2014 CodeEngn Conference 10] 노용환 - 디버거 개발, 삽질기GangSeok Lee
2014 CodeEngn Conference 10
MS 에게 속았어요
Windows 운영체제가 지원하는 디버거 지원 기능들과 브랜치 트레이서를 구현하기 위한 몇 가지 방법들을 소개하고, Windows 커널에 이미 구현되어있는 하드웨어 기반 브랜치 트레이서 코드 분석과 여기에 존재하는 의도된(?) 버그를 살펴본다.
http://codeengn.com/conference/10
http://codeengn.com/conference/archive
[2014 CodeEngn Conference 11] 박한범 - 가상화 기술과 보안GangSeok Lee
2014 CodeEngn Conference 11
가상화와 보안의 합작
가상화 기술은 대상체를 추상화된 리소스로 가상화하여 활용할 수 있는 기술이다. 가상화 기술이 하드웨어 차원에서 지원되기 시작한 이후로 CPU가 제어하는 자원을 하드웨어 레벨에서 가상화 할 수 있게 되었다. CPU가 하드웨어 수준에서 가상화를 지원하기 위해 설계된 구조와 인터페이스가 존재하는 계층이 기존에 운영체제에서 사용하던 Ring 0~3 계층 상위에 추가되면서 이를 보안에서 활용하는 시도들이 있어왔으며 대표적으로 ARM TrustZone 아키텍처가 있다. TrustZone과 같은 아키텍처는 운영체제와는 다르게 오직 보안에 관련된 서비스와 기능만을 탑재한 보안전용운영체제를 먼저 상주시킨다. 운영체제가 특권/사용자 계층을 나누어 사용자 계층에서 하드웨어 자원에 접근하는 것을 막고 대신 요청을 받아 처리함으로서 하드웨어 자원을 보호했던 것과 유사하게 보안/일반 계층으로 나눠 보안이 필요한 동작시에 보안전용운영체제가 요청을 받아 처리하는 구조를 갖고, 일반 계층은 격리되어 보안 계층에 접근할 수 없으므로 보안성을 한층 높힌 구조이다. 본 발표는 가상화 기술에 대한 개괄적 설명과 이를 활용한 PS/2 키로거를 제작 I/O를 가로채는 과정을 살펴보고 운영체제 상위 권한이 어떤 의미를 갖는지 그리고 CPU하드웨어 레벨의 강력한 권한을 체험하는 것을 통해 가상화 기술의 특성을 파악해보자 한다.
http://codeengn.com/conference/11
http://codeengn.com/conference/archive
본 발표자료에서는 이더리움 플랫폼의 상세 아키텍쳐와 기반 기술, 그리고 스마트 컨트랙과 이를 기반한 Dapp의 개발 방안에 대해 소개한다. 이더리움은 블록체인 기반 기술하에 암호 화폐의 생성 , 전송 등 라이프사이클 관리외에 스마트 컨트랙을 지원한다. 스마트컨트랙은 서로 모르는 당사자간의 계약을 준수하도록 강제할 수 있는 응용 프로그램이다. 컨트랙 프로그램은 바이트코드로 컴파일된 후 블록체인을 통해 배포되고 , 로컬 로드상에서 실행되는 일종의 에이전트라 볼 수 있다. 이렇게 개바된 스마트컨트랙은 기존 웹 인터페이스를 통해 접근하고 활용할 수 있으며 이렇게 스마트 컨트랙 기반하에 개발된 응용 서비스를 Dapp이라 한다.
GCGC- CGCII 서버 엔진에 적용된 기술 (6) - CGCII Server Sample
1. Sample ServerCGCIICho sanghyun’s Game Classes II
1. Component of CGCII Server System
2. Simple Server
3. Simple Client
4. Message Sending/Reading
5. Easy to development
2. CGCIICho sanghyun’s Game Classes II
실행처리 CGCII Server System (1)
• 접속을 받는 Socket 객체
• 접속이 들어오면 내 부적으로 NEW<TSOCKET> 으로 소켓 객체를 생성해서 접속 처
리 !
• Socket 객체
• TSOCKET 을 묶어서 관리해줄 객체
// 1) Socket 을 NEW<> 를 사용해서 생성
CGPTR<CSocket> pSocket = NEW<CSocket>()
…
// 2) 접속된 Socket 으로 메시지 전송하려 하면 ..
pSocket->Send([ 전송할 내용 ])
// 1) Socket 을 NEW<> 를 사용해서 생성
CGPTR<CSocket> pSocket = NEW<CSocket>()
…
// 2) 접속된 Socket 으로 메시지 전송하려 하면 ..
pSocket->Send([ 전송할 내용 ])
• 재정의 가능한 다양한 virtual 로 선언된 훅 함수들이 존재함 .
virtual void OnConnect()→ 접속될 때 호출됨
virtual void OnFailConnect() → 접속실패 때 호출됨
virtual void OnDisconnect () → 접속 종료될 때 호출됨
virtual void OnMessage(…) → 메시지 전송되어 오면 호출됨
3. CGCIICho sanghyun’s Game Classes II
실행처리
class CSocket :
public CGNetSocket::CTCP<>
{
private:
virtual void OnConnect() { printf(“ 접속되었다” );}
virtual void OnDisconnect() { printf(“ 접속 종료되었다 .”);}
virtual DWORD OnMessage(CGMSG& p_rMSG) { printf(“ 메시지 왔다 .”); return TRUE;}
};
class CSocket :
public CGNetSocket::CTCP<>
{
private:
virtual void OnConnect() { printf(“ 접속되었다” );}
virtual void OnDisconnect() { printf(“ 접속 종료되었다 .”);}
virtual DWORD OnMessage(CGMSG& p_rMSG) { printf(“ 메시지 왔다 .”); return TRUE;}
};
3. 훅 (Hook) 함수를 재정의 한다 .
OnConnect: 접속되었을 때 호출
OnDisconnect: 접속종료 되었을 때 호출
OnMessage: Message 가 도착했을 때 호출
1. Socket Class 를 상속받는다 .
Server Coding (1)
#include "stdafx.h"
#include "Socket.h"
CGOBJ<CGNetAcceptor::CBase<CSocket>> g_acceptor;
int _tmain(int /*argc*/, _TCHAR* /*argv*/[])
{
g_acceptor.Listen(20000);
while(_getch()!=27);
return 0;
}
#include "stdafx.h"
#include "Socket.h"
CGOBJ<CGNetAcceptor::CBase<CSocket>> g_acceptor;
int _tmain(int /*argc*/, _TCHAR* /*argv*/[])
{
g_acceptor.Listen(20000);
while(_getch()!=27);
return 0;
}
3. Acceptor 선언
4. 20000 번 port Listen 시작
5. ESC 누를 때까지 대기 !
끝
,
public NCGPoolable<CSocket>
2. Pool 에서 할당받도록…
4. CGCIICho sanghyun’s Game Classes II
실행처리 Server Coding (2)
이걸로 서버 동작 !
특별한 초기화하지 않아도 기본
Thread, Pool, Socket 등등 내부적으로 초기화 처리됨 !
이보다 더 쉬울 수 있나요 ?
5. CGCIICho sanghyun’s Game Classes II
실행처리
class CSocket :
public CGNetSocket::CTCP<>,
public CGNetIO::Connector::NTCP
{
private:
virtual void OnConnect() { printf(“ 접속되었다” );}
virtual void OnFailConnect() { printf(“ 접속실패 !”);}
virtual void OnDisconnect() { printf(“ 접속 종료되었다 .”);}
virtual DWORD OnMessage(CGMSG& p_rMSG) { printf(“ 메시지 왔다 .”); return TRUE;}
};
class CSocket :
public CGNetSocket::CTCP<>,
public CGNetIO::Connector::NTCP
{
private:
virtual void OnConnect() { printf(“ 접속되었다” );}
virtual void OnFailConnect() { printf(“ 접속실패 !”);}
virtual void OnDisconnect() { printf(“ 접속 종료되었다 .”);}
virtual DWORD OnMessage(CGMSG& p_rMSG) { printf(“ 메시지 왔다 .”); return TRUE;}
};
3. OnFailConnect() 추가 . 나머지는 똑같음 .
1. 동일하게 Socket Class 를 상속받는다 .
Client Coding (1)
#include "stdafx.h"
#include "Socket.h"
CGOBJ<CSocket> g_socket;
int _tmain(int /*argc*/, _TCHAR* /*argv*/[])
{
g_socket.Connect(“localhost”, 20000);
while(_getch()!=27);
return 0;
}
#include "stdafx.h"
#include "Socket.h"
CGOBJ<CSocket> g_socket;
int _tmain(int /*argc*/, _TCHAR* /*argv*/[])
{
g_socket.Connect(“localhost”, 20000);
while(_getch()!=27);
return 0;
}
4. Socket 선언
5. local host:20000 번에 접속 시도한다 .
2. IConnector 도 상속받는다 .(Connect 기능을 위해 )
CGExecutor::Default::InitInstance(CGEXECUTOR_NOTHREAD);
for(;;)
{
CGExecutor::Default::RunExecutor();
if(_kbhit()==1 && _getch()==27) break;
}
Ex2) No-Thread 이므로 매번 호출해주어야 함 !
Ex1) No-Thread 로 동작하기 위한 설정 !
( 이걸 설정하지 않으면 자체 Thread 를 생성해
서 처리됨 .)
6. ESC 누를 때까지 대기 !
No Thread 로 동작시키고 싶다면 ?No Thread 로 동작시키고 싶다면 ?
역시 끝
6. CGCIICho sanghyun’s Game Classes II
실행처리
접속 때 MESSAGE_CHATTING 메시지를 전송하게 하려면…
void CSocket::OnConnect()
{
CCGBuffer bufSend = MEM_POOL_ALLOC(1024);
bufSend.Append<WORD>();
bufSend.Append<WORD>(MESSAGE_CHATTING);
bufSend.Append<int>(5);
bufSend.AppendString<char>(“Hello CGCII World”);
bufSend.SendMessageLength();
Send(bufSend);
}
void CSocket::OnConnect()
{
CCGBuffer bufSend = MEM_POOL_ALLOC(1024);
bufSend.Append<WORD>();
bufSend.Append<WORD>(MESSAGE_CHATTING);
bufSend.Append<int>(5);
bufSend.AppendString<char>(“Hello CGCII World”);
bufSend.SendMessageLength();
Send(bufSend);
}
1. CCGBUFFER 에 메모리를 할당한다 .
Message Sending (1)
2. Append 를 사용해서 전송할 메시지를 작성한다 .
3. 전송한다 .
7. CGCIICho sanghyun’s Game Classes II
실행처리
구조체로 써넣는 방법은 기본적으로 지원한다 .
void CSocket::OnConnect()
{
SMESSAGE_TEST temp;
temp. sizeMessage = sizeof(SMESSAGE_TEST);
temp. wMessage = MESSAGE_TEST;
temp. iValue = 5;
CCGBuffer bufSend = MEM_POOL_ALLOC(sizeof(SMESSAGE_TEST));
bufSend.Append<SMESSAGE_TEST>(temp);
Send(bufSend);
}
void CSocket::OnConnect()
{
SMESSAGE_TEST temp;
temp. sizeMessage = sizeof(SMESSAGE_TEST);
temp. wMessage = MESSAGE_TEST;
temp. iValue = 5;
CCGBuffer bufSend = MEM_POOL_ALLOC(sizeof(SMESSAGE_TEST));
bufSend.Append<SMESSAGE_TEST>(temp);
Send(bufSend);
}
Message Sending (2)
1. struct 를 선언해 값을 설정
2. Append 로 한번에 써넣는다 .
3. 전송한다 .
struct SMESSAGE_WELCOME
{
WORD sizeMessage;
WORD wMessage;
int iValue;
};
struct SMESSAGE_WELCOME
{
WORD sizeMessage;
WORD wMessage;
int iValue;
};
9. CGCIICho sanghyun’s Game Classes II
실행처리
받은 MESSAGE_WELCOME 메시지를 읽기…
void CSocket::OnMessage(CGMSG& p_rMSG)
{
CGNETMSG& rMSG = (CGNETMSG&) p_rMSG;
CCGMemoryPtr ptrBuffer = p_rMSG.Buffer;
WORD wSize = ptrBuffer.ExtractHead<WORD>();
WORD wMessage = ptrBuffer.ExtractHead<WORD>();
int iValue = ptrBuffer.ExtractHead<int>();
const char* strValue = ptrBuffer.ExtractHeadString<char>();
…
}
void CSocket::OnMessage(CGMSG& p_rMSG)
{
CGNETMSG& rMSG = (CGNETMSG&) p_rMSG;
CCGMemoryPtr ptrBuffer = p_rMSG.Buffer;
WORD wSize = ptrBuffer.ExtractHead<WORD>();
WORD wMessage = ptrBuffer.ExtractHead<WORD>();
int iValue = ptrBuffer.ExtractHead<int>();
const char* strValue = ptrBuffer.ExtractHeadString<char>();
…
}
1. CGNETMSG 로 Casting 한다 .
Message Reading (1)
2. 임시 포인터를 선언해 Buffer 의 포인터를 넣는다 .
3. 값들을 Extract 해낸다 .
10. CGCIICho sanghyun’s Game Classes II
실행처리
Offset 을 알 경우 바로 값을 읽을 수 있다 .
void CSocket::OnMessage(CGMSG& p_rMSG)
{
CGNETMSG& rMSG = (CGNETMSG&) p_rMSG;
WORD wSize = rMSG .Buffer.Head<WORD>(0);
WORD wMessage = rMSG .Buffer.Head<WORD>(2);
int iValue = rMSG .Buffer.Head<int>(4);
const char* strValue = rMSG .Buffer.GetHeadString<char>(8);
…
}
void CSocket::OnMessage(CGMSG& p_rMSG)
{
CGNETMSG& rMSG = (CGNETMSG&) p_rMSG;
WORD wSize = rMSG .Buffer.Head<WORD>(0);
WORD wMessage = rMSG .Buffer.Head<WORD>(2);
int iValue = rMSG .Buffer.Head<int>(4);
const char* strValue = rMSG .Buffer.GetHeadString<char>(8);
…
}
Message Reading (2)
내부 포인터를 옮기지 않고 직접 읽기 .
Offset 을 알면 직접 값을 읽을 수 있다 .
11. CGCIICho sanghyun’s Game Classes II
실행처리 개발하기 쉽다란 ? (1)
그렇다면
진짜 개발이 쉽다란 ?
진짜 이보다 더 쉬울 수 있을 까요 ?
Of Course!
문법적으로 더 간결한 코드로 구현이 가능하다 ?
→ 원초적 도구 논쟁 JAVA, C++, C# 등등 …
12. CGCIICho sanghyun’s Game Classes II
실행처리 개발하기 쉽다란 ? (2)
→ 필요한 기능이 구현된 풍부한 라이브러리가 있다 .
→ 검증된 코드와 충분한 참고자료가 존재한다 .
→ 경력자의 입장에서는 익숙함 !
→ 초보자의 입장에서는 대세 개발 방법이 뭐냐 ?
∵ 기타 디버깅이 쉽다 , 안정적이다 , 싸다 등등은 각자 결론 정해
놓고 좋을 대로 끼워맞추는 용도 !
대부분은 기능의 문제에 관심 !!
한걸음 더 나아가면 심리적 요인 !
사장님의 내면적 요인도 존재 !
→ 개발 인력을 쉽게 찾을 수 있나 !
→ 개발 리스크는 적은가 ?
→ 기능 구현의 문제가 가장 중요한 문제임을 부정할 순 없음 .
13. CGCIICho sanghyun’s Game Classes II
실행처리 개발하기 쉽다란 ? (3)
→ 쉬운 개발이란 문법적 간결성의 문제일 수 있다 .
코드가 대여섯 줄이라면…
→ 기능 구현의 문제일 수 있다 .
아주 단순한 기능만 구현하는 프로그래밍이라면…
하지만 게임 서버는 점점 복잡해져만 가고…
문제는 적은 코드 작성의 문제 혹은 기능 구현의 문제가 아닌
→ 보다 단순한 모델인로 파악할 수 있도록 하는 시도 !
→ 복잡성 해결의 문제 !
14. CGCIICho sanghyun’s Game Classes II
실행처리 개발하기 쉽다란 ? (4)
기존 프로그래밍에 비해 Structured Programming 이 개선한 것은 ?
<Iteration><Selection><Sequence>
→ 생산성 개선은 문법적 간결성이나 재사용성에 대한 것이
아닌 이해 , 수정 , 검증의 개선으로…
→ 소프트웨어를 순차진행 , 선택 , 반복 3 요소의 직렬화
만으로 설계하는 것이 핵심 .
Call
Call
Return
R
eturn
인지의 흐름
15. CGCIICho sanghyun’s Game Classes II
실행처리 개발하기 쉽다란 ? (5)
Object Oriented Programming 이 개선한 것은 ?
소프트웨어를 독립된 함수들의 나열이 아니라 객체들 간의 관계로 이해할 수 있도록 해준다 .
Connect (…)
Accept (…)
SendBuffer (…)
SendString (…)
ReceiveString (…)
Close (…)
Open (…)
기능의 나열 프레임워크
객체간의 관계
확장성 & 유연성
재정의와 합성
• 복잡성 문제 대응 용의
• Design Patterns
• but 특화문제
조금만 제작된 용도와 다른 용도로
사용하려 하면 오히려 족쇄
• 기능적 문제 해결 수준
• 소프트웨어 대형화로 인한 복잡
화문제 대응에 한계
• 객체 조합과 합성 그리고
Generics
• CGCII 는 OOP 와 Generics 를
최대한 활용한 개방적 구조 .
OOP 는 복잡성에 대한 개선에 대한 또 다른 접근…