[Line Developer Day 2021] TCP로 인한 대규모 Kafka 클러스터 요청 지연 문제 해결 사례

Woong·2021년 12월 15일
0

컨퍼런스/세미나

목록 보기
5/12

TCP로 인한 대규모 Kafka 클러스터 요청 지연 문제 해결 사례

배경

  • Kakfa 는 높은 확장성, ACL, Quota, 멀티 테넌트 운영 가능.

    • (Kafka에 대한 설명 생략. Producer, broker ,consumer 등 기초적인 내용.)
  • 라인 광고, 공식 계정 등 100개 이상의 라인 서비스를 kafka cluster 의 유저로 삼음.

문제 발생과 원인 파악

  • 메시지를 카프카에 timeout 문제로 송신할 수 없는 문제가 발생 -> 크리티컬한 문제임.

  • 브로커에서 나타나는 메트릭은 정상적이었음. (응답타임 정상)

  • 레플리카가 여럿 죽어 리젝트가 일어났는가? 아니었음.

  • 그런데 broker 응답 타임은 정상으로 나타나는데, 프로듀서에서 측정되는 응답타임은 16초 가량으로 굉장히 컸음.

  • 프로듀서에서 특정 브로커에 프로듀싱할 때에먼 high latency 가 나타았음.

  • 어떤 브로커를 재시작한 직후부터 악화되기 시작하였으나, 정작 그 브로커 메트릭에선 정상으로 나타난 것. 해당 브로커를 재시작하자 해당 현상은 없어졌음.

  • kafka 소스코드 분석으로 request 송신 자체가 오래 걸리면 이러한 갭이 발생한다는 결론을 얻음.

    • broker 는 메시지를 완전히 수신받고 나서 측정을 시작하므로.

request 송신 자체가 지연된 이유는?

  • node_netstat_TcpExt_Cookies 라는 수치가 급증한 것이 확인됨.

배경지식 - TCP SYN Cookies

  • TCP SYN Cookies 는 TCP 3-way handshake 에서 사용되는 개념.

  • ack 를 악의적으로 보내지 않아 SYN Queue 를 full 시키는 것이 syn flood attack이고.

  • TCP SYN Cookies 는 SYN Queue가 다 차면 queue 에는 넣지 않고 SYN+ACK 에 syn coockies 를 인코딩하여 같이 넣고, forget 함.

    • ACK 를 받으면 SYN Cookies 를 디코딩하여 handshake 완료함.

TCP SYN Cookies가 영향을 미친 과정

  • 브로커를 재시작했을 때, 해당 클라이언트(프로듀서)에서는 다른 브로커로 fail over 하고,
    브로커가 재시작 완료되고 나서 자연적으로 SYN flood 가 발생한 것 -> 일부 브로커가 syn cookies 를 사용하는 상태가 됨.

  • SYN Cookies 를 사용하면 시퀀스 넘버가 32비트밖에 안되어서 window scaling 을 사용할 수 없음.

  • window scaling factor 가 무효화되더라도 65535 보다 확대하기 위한 기능이기 때문에 해당 부분만 문제가 되는가? 라는 의문이 발생. (이미 충분한 수치라고 판단)

  • 모든 connection 을 SYN Cookies 를 사용하도록 강제한 다음 테스트 시행.

  • TCP Timestamp 무효화 하기 전 상태(=window scaling 이 유효한 상태)에서 동일하게 발생.

  • 실제 window 사이즈는 789* 2^(window scaling factor) 값임

  • 그런데 scaling factor 가 1이 되어 매우 작은 값이 된 것이 확인됨.

  • ss 에 -i 옵션을 줘서 tcptimestamp, window scaling 에 대한 정보를 볼 수 있어 이를 통해 확인함.

  • 그런데 브로커에서는 scaling factor 가 7로 나옴.

    • -> 양측이 보유한 값이 서로 다름
    • -> 반드시 서로 같아야하므로 어느 한쪽이 문제가 생긴 것.
  • BPF + kprobe 로 커널 함수를 후킹하여 확인한 결과, 브로커에서는 7로 계산한 것으로 확인됨.

  • 리눅스 커널 5.10 버전 이전에서 발생한 커널 함수 버그로 브로커가 SYN-ACK 를 보낼 땐 1로 보냈지만, ACK 를 받은 후 scaling factor 가 7로 override 된 것.

  • 프로듀서의 윈도우 사이즈가 브로커 대비 7배나 작았기 때문에 프로듀서가 요청을 보내는데 상당히 오래 걸리는 현상이 발생함.

해결방법

  • 이를 해결하기 위해 SYC Cookies 를 무효 처리하려함 -> SYN Queue full 상태로 인한 딜레이 발생
  • 이에 더해 kafka 의 listen backlog size 를 늘려 syn flood 자체를 방지하려함 -> 하지만 Kafka 에서 50으로 하드코딩되어 이이상 늘릴 수가 없어 KIP 제안 진행중.

0개의 댓글