티스토리 뷰

반응형

MTProto Mobile Protocol

 

https://core.telegram.org/mtproto

 

General Description


이 프로토콜은 모바일 디바이스에서 서버로 접근하는 API로 디자인 되었다. 웹 브라우저에서 사용하는 것이 아님을 강조한다.

이 프로토콜은 3개의 독립된 컴포넌트로 세분화 되어 있다.
. 하이레벨 컴포넌트(API query language) : API쿼리와 메시지가 바이너리로 변환된 내용이 정의 되어 있다.
. 암호화 계층(인증) : 전송되기 전에 암호화된 메시지의 내용이 정의 되어 있다.
. 전송 컴포넌트 : 클라이언트와 서버간의 전송을 위해 다른 기존의 네트워크 프로토콜(예: http, https, tcp, udp)에 대한 내용이 정의되어 있다.

 

노트 1:
일반 텍스트 메시지를 MTProto에서 항상 암호화하고, 시스템 구성 요소와 알려진된 문제에 대해 강력하도록 암호 해독 시 검사할 다음 데이터를 포함한다.
•server salt (64-Bit) : 서버슬랫
•session id : 세션아이디
•message sequence number : 메시지 순번
•message length : 메시지 길이
•time : 시간

 

노트 2:
추가 커맨트를 보려면 링크 클릭

 

 

Brief Component Summary : 구성 요소 요약
High-Level Component (RPC Query Language/API) : 하이레벨 컴포넌트
하이레벨 컴포넌트 관점에서 보면, 클라이언트와 서버 세션안에서 메시지 교환하는 것이다.
세션은 특정 http/https/tcp 연결 보다는 오히려 클라이언트 장치 (더 정확 하 게, 응용 프로그램)에 연결 된다.
또한, 각 세션은 실제 인증완료된 사용자 키 ID에 연결되어 있다.

여러 서버에 연결을 열릴 수 있고, 메시지는 어떤 컨넥션이든지 양방향으로 전송이 가능하다.
(응답은 동일한 연결을 통해서 반환되지 않을 수 있으며, 자주 발생하는 경우이다. 그러나, 다른 세션을 통해서라도 메시지가 반환 될 수 있다.)
UDP 프로토콜을 사용하는 경우 응답 쿼리가 다른 IP 주소에 의해 반환 될 수 있다.

몇개의 메시지 유형
•RPC calls (client to server): 클라이언트가 서버 API호출
•RPC responses (server to client): 클라이언트 호출에 대한 결과 반환
•Message received acknowledgment (or rather, notification of status of a set of messages) : 메시지 수신 승인(또는 알림 메시지 집합)
•Message status query : 메시지 상태 쿼리
•Multipart message or container (a container that holds several messages; needed to send several RPC calls at once over an HTTP connection, for example; also, a container may support gzip).
멀티파트 메시지 또는 컨테이너(컨테이너는 여러개의 메시지를 홀드 할 수 있고, 서버로 한번에 보낼 수 있다. 예를 들어 컨테이너가 gzip을 지원하는 경우다)

 

낮은 레벨 프로토콜의 관점에서 메시지는 이진 데이터 스트림 4 또는 16 바이트 경계에 따라 정렬된다.
메시지의 첫부분 몇 가지 필드는 암호화/인증 시스템에 의해 사용되도록 고정되어있다.

각 메시지는, 독립적이거나 컨테이너 내부는 메시지 식별자(64비트, 아래 참조), 메시지 세션의 순번(32비트), 길이(바이트;메시지 본문의 길이 32비트), 본체(4바이트의 배수)로 구성되어진다.
또한, 컨테이너 또는 단일 메시지를 보낼 때 내부 헤더가 상단에 추가 되고(아래 참조), 메시지가 암호화되고, 외부헤더가 메시지 상단에 들어 갑니다.(64-비트 키 식별자와 128-비트 메시지 키)

메시지 본체는 일반적으로 종속 매개 변수 뒤에 32비트 메시지 유형으로 구성되어있고,
특히 각 RPC 함수는 해당 메시지 유형이 있다. 자세한 사항은 링크 참고

모든 숫자는 리틀 엔디안으로 작성 된다. 그러나, 매우 큰 숫자 (2048 비트) RSA와 DH는 큰 endian 형식으로 작성 된다. 왜냐하면 OpenSSL 라이브러리이기 때문이다.

 

Authorization and Encryption : 인증과 암호화

 

이전 메시지 (또는 다중 파트 메시지) 전송 프로토콜을 사용 하여 네트워크를 통해 전송 되고, 암호화된 외부 헤더는 메시지의 위쪽에 추가 된다. 암호화된 내용은 64-비트 키 식별자 (고유 하 게 식별 인증 키 서버 뿐만 아니라 사용자에 대 한) 및 128 비트 메시지 키이다. 사용자키와 메시지키 256비트 키를 정의하고, 실제 메시지를 AES-256 방식으로 암호화한다.
메시지 암호화의 초기 부분 메시지 키(및 그러므로 AES 키 및 iv)와 명백 하게 영향을 미치는 변수 데이터(세션, 메시지 ID, 시퀀스 번호, 서버 소금) 포함 되어 있있다. 메시지 키가 메시지 본문의 SHA1 128 하위 비트로 정의 (포함 한 세션, 메시지 ID, 등.). 다중 파트 메시지를 단일 메시지 암호화

기술 사양에 대한 모바일 프로토콜(링크)을 참조

클라이언트 응용 프로그램이 처음으로 해야하는 것은 인증키를 생성해야한다. 일반적으로 이 과정은 변하지 않는다.

 

프로토콜의 주요한 결점은 침입자가 수동적으로 메시지를 차단하고, 어떻게든 인증키(예를 들어 장치를 훔쳤을 때)를 도용하여 메시지를 가로체고 해독할 수 있다. 아마도 이건 너무 많은 문제(장치를 훔치면 저장된 모든 정보를 모두 해독할 수 있다)를 가지고 있다. 그러나, 이 약점을 극복하기 위해 다음 단계를 수행하면 된다.

 

* 세션키는 Diffie-Hellman 프로토콜에 의해 생성하고, 인증과 메시지키는 AES 파라메터에서 선택해서 사용한다.
이 것을 만든 후 클라이언트는 첫번째로 새로운 세션을 생성하고 RPC서버로 전송하면, 서버가 생성된 세션키를 반환해준다.그 후 모둔 후속 메시지는 세션 키를 사용하여 암호화 된다.

 

* 클라이언트 장치에 저장된 키를 택스트 암호로 보호한다. 이 패스워드는 메모리에 저장되지 않고 사용자에 응용프로그램이 시작될 때 입력 받는다.

 

* 사용자 장치에 저장된 데이터 또한 인증키를 이용해서 암호화해서 보호해야 한다. 패스워드는 그 데이터에 접근할 때도 필요하다

 

Time Synchronization : 시간 동기화

 만약 클라이언트 시간과 서버 시간이 차이가 많이 난다면, 서버는 클라이언트 메시지를 무지하거나, 그 반대의 경우가 발생할 수 있다. 왜냐하면, 메시지 식별자가 잘못되었기 때문이다(생성시간과 밀접한 관련이있다)

이러한 상황에서 서버는 클라이언트에게 정확한 시간을 포함하는 특별한 메시지와 128-bit salt를 보낸다.
(클라이언트 특정 RPC 동기화 요청을 받거나 현재 세션 중에 받은 마지막 메시지의 키와 같은지 비교해서 명시적으로 제공한다.)

이 메시지는 다른 메시지를 포함하는 컨테이너의 첫번째가 될 수 있다.(시간 차이가 중요하지만 클라이언트의 메시지가 발생하지 않은 경우 무시된다.)

 

그러한 메시지 또는 그것을 포함한 컨테이너를 수신한 경우, 클라이언트는 우선 시간 동기화를 수행(서버시간과 미래의 올바른 시간을 계산하고 차이를  이용해서 보정)하고 메시지 식별자가 정확한지 검사한다.

 

보정이 무시 경우, 클라이언트는 메시지 식별자 단순성을 보장하는 새로운 세션을 생성한다.

 

Transport : 전송

클라이언트에서 서버로나 그 반대로 암호화된 컨테이너와 외부 헤더(이하 페이로드)의 전달이 가능하다. 세가지 전송 타입이 있다.
. HTTP

. TCP

. UDP
우선 두가지 종류를 살펴보자

 

HTTP Transport

HTTPS를 사용하지 않고 기존의 TCP 포트 80을 이용하는 HTTP/1.1(with keepalive)로 구현; 위의 암호화 방법이 대신 사용된다.

 

HTTP 연결은 가장 최근에 수신된 사용자 쿼리에 지정된 세션(아니면 세션 + 키 식별자)에 붙어있다. 일반적으로 세션은 모든 쿼리에서 동일하지만, HTTP 프록시에 의해 손상될 수 있다. 서버는 HTTP 연결에서 동일한 세션이 아니거나, 서버의 차례가 아니면 메시지를 반환하지 않는다.(클라이언트의 HTTP 요청을 받고 응답을 하지 않은 상태)

다음은 전반적인 사항이다. 클라이언트는 서버에 하나 이상의 keepalive HTTP 연결을 연다.만약 하나나 그 이상의 메시지를 보내야 하는 경우, POST 요청을 포함하는 페이로드를 만들고 전송한다. 페이로드에는 컨텐츠길이, Keepalive와 호스트의 유효한 HTTP헤더를 추가한다.

 

쿼리를 수신하면, 서버는 조금 기다리거나(만약 쿼리가 짧은 타임아웃 응답을 요구하면) 즉시 더미 응답(오직 컨터이너가 인정된 경우)을 반환한다. 어떤 경우에는, 응답 메시지에 임의의 수를 포함 할 수있다. 서버는 동시에 세션에서 홀딩 중이던 다른 메시지를 전송할 수 있다.

 

또한, 최대 전송 타임아웃 T가 지정된 특정 long poll RPC쿼리(유효한 HTTP 연결만 가능)가 존재한다. 일반적으로 서버가 세션에 메시지를 가지고 있다면 즉시 반환한다. 그러나 long poll RPC쿼리가 존재하면, T second가 흐르기 전까지 서버는 메시지를 대기 상태로 만든다. 만약 T seconds가 흐른 후 이벤트가 발생하지 않으면 더미 응답을 반환한다(특별 메시지).

 

만약, 서버가 클라이언트에서 메시지를 보내야할 필요가 있다면, 필요 세션과 "HTTP 요청에 응답가능" 상태, HTTP연결을 확인하고, 메시지를 응답 컨테이너에 넣은 후 사용자에게 보낸다. 전형적으로 서버에서 또 다른 메시지를 보내기 위해서는 추가 시간(50밀리세컨드)이 필요하다. 

 

만약 어떤 적합한 HTTP 연결을 사용할 수 없다면, 메시지는 현재 세션의 송신 큐에 담긴다. 그러나, 그 메시지들은 명시적이든 간접적으로 클라이언트에 확인될 때까지 어떻게든 자신의 길을 찾는다. HTTP 프로토콜에서, 동일한 HTTP 연결안에서 다음 쿼리를 전송하면 암묵적 확인 응답으로 간주한다.(아무것도 없다면 HTTP 프로토콜은 명시적 승인을 요청을 보낸다), 다른 경우에, 클라이언트는 일정 시간 내에 명시적 확인 응답을 반환해야한다(그것이 다음 요청을 컨터이너에 추가할 수 있다)

 

중요 : 만약 응답 시간에 승인 메시지가 도착하지 않을 경우, 메시지를 재정송할 수 있다.(다른 컨테이너를 이용해서). 당사자들은 자율적으로 이에 대한 준비를해야하고, 가장 최근의 수신된 메시지 식별자를 저장해야한다.(반복된 동작에 의해 발생되는 중복은 무시) 저장된 영원한 식별자는 가질 수 없기 때문에, 메시지 식별자의 단순성을 활용 특수 가비지 컬력션 메시지가 존재한다.

만약 송신 큐가 오버플로우가 발생하거나 메시지가 큐에 10분이상 남아있다면 서버는 그것들을 지운다.(아니면 스왑한다.) 이 것은 서버의 버퍼 공간이 부족한 경우 더 빠르게 발생할 수 있다.(예를 들어 네트워크 이슈가 발생했다거나 할 때)

 

TCP Transport

이것은 HTTP 전송과 매우 유사하다. 또한 포트 80(모든 방화벽을 통과하기 위해)과 동일한 IP 어드레스를 사용한다. 이 상황에서, 서버는 HTTP또는 TCP프로토콜 중 어떤 것을 사용해야하는지 처음 4바이트를 기준으로 판단한다.(HTTP POST방식)

 

TCP연결이 생성되면, 이 세션(과 인증키)을 사용자 메시지 전송에 할당하고, 이어서 독점적으로 이용한다.(다중화 배열이 허용되지 않는다)

 

만약 페이로드가 서버에서 클라이언트, 혹은 클라이언트에서 서버로 전송될 필요가 있는 경우에 다음과 같이 캡슐화: 4바이트(길이, 순번, CRC32;4로 나누어지는)를 앞에 추가, TCP 컨넥션에서의 패킷 순번 4바이트(처음건 0, 다음은 1..), 4 CRC32 바이트(길이, 순번, 페이로드)를 뒤에 추가

 

동일한 프로토콜의 축소된 버전이 있다: 만약 클라이언트가 0xef를 첫번째 바이트로 보내면(**중요** 첫데이터 패킷이전에), 패킷 길이는 암호화 된다.(0x01..0x7e = 데이터 길이는 4로 나누거나 0x7f 다음 3바이트를 4로 나눈). 이 경우 서버는 동일한 응답을 보낸다.

 

프로토콜의 전체 및 축소 버전의 빠른 응답을 지원해야한다. 이 경우, 클라이언트는 질의 패킷에서 가장 높은 차수 비트 길이를 설정하고, 서버는 개별 패킷의 특정 4바이트로 응답한다. 그것들은 정규 서버 응답 패킷이 아니라는 것을 명확하게 설정하는 최상위 비트를 가진 패킷의 암호화 부의 고차 SHA1비트이다; 축소 버전의 경우 4바이트에 적용된다.

 

TCP 전송에에는 묵시적 승인은 없다 : 모든 메시지를 명시적으로 승인해야한다: 컨테이너나 응답을 빠르게 승인해야한다. 예를 들어 거의 항상 RPC쿼리를 포함하는 클라이언트 메시지 : 확인 응답은 보통 RPC 응답으로 처리

 

에러가 발생하면, 서버는 페이로드 에러 코드로 4 바이트로 구성 패킷을 전송할 수있다. 예를 들어, 오류 코드 (403)는 해당 HTTP 에러가 HTTP 프로토콜에 의해 반환 될 상황에 대응한다.

반응형

'Previous Platforms > ETC' 카테고리의 다른 글

Image Note  (0) 2014.05.12
Now FocusedElement, CurrentPage  (0) 2013.08.29
Custom ConfirmBox create  (0) 2013.08.21
patterns & practices: Prism for the Windows Runtime  (0) 2013.07.10
Microsoft .Net Framework 4.5 Quickstart Cookbook Review  (0) 2013.07.05
댓글