nginx 의 epoll

6160 단어
nginx 학습 의 epoll
먼저 전통 적 인 I / O 다 중 재 활용 select 와 poll 을 말 하고 epoll 과 의 차 이 를 비교 해 보 세 요.
예 를 들 어 100 만 명의 사용자 가 한 프로 세 스 와 동시에 TCP 연결 을 유지 하고 매 순간 몇 십 개 또는 몇 백 개의 tcp 연결 만 활발 하 다 면 (즉, TCP 패 키 지 를 받 을 수 있다) 매 순간 프로 세 스 는 이 100 만 개의 연결 중 일부분 만 처리 해 야 합 니 다.
select 와 poll 은 이렇게 처리 합 니 다. 어느 순간 프로 세 스 는 모든 연결 을 수집 합 니 다. 사실 이 100 만 연결 중 대부분 사건 이 발생 하지 않 았 습 니 다.따라서 이 벤트 를 수집 할 때마다 100 만 개의 연 결 된 소켓 을 운영 체제 에 전송 한다 면 (이것 은 우선 사용자 상태 메모리 에서 커 널 메모리 로 의 대량 복사) 운영 체제 커 널 에서 이 링크 에 처리 되 지 않 은 이 벤트 를 찾 는 것 은 큰 낭비 가 될 것 이다.
epoll 은 이렇게 합 니 다. epoll 은 select 와 poll 을 두 부분 으로 나 누 었 습 니 다.
1 、 epoll 호출creat 에서 epoll 대상 을 만 듭 니 다.
2, epoll 호출ctl 은 epoll 대상 에 100 만 개의 연결 소켓 을 추가 합 니 다.
3 、 epoll 호출wait 이벤트 가 발생 한 연결 을 수집 합 니 다. =포 인 트 는 여기 있 습 니 다. epoll 호출wait 는 발생 하 는 모든 이벤트 의 연결 을 수집 하고 이 벤트 를 하나의 링크 에 넣 습 니 다. 이 링크 에서 100 만 개의 연결 을 옮 겨 다 니 지 않 고 연 결 된 이 벤트 를 찾 아야 합 니 다!이렇게 실제 사건 을 수집 할 때 epollwait 효율 이 높 을 겁 니 다.
세 시스템 호출 함 수 는 모두 C 로 포장 되 어 있 으 며, P310 에서 함수 에 의 해 상세 하 게 설명 되 어 있 으 며, 다음은 간단하게 소개 합 니 다.
**int** epoll_create(**int** size);    
**int** epoll_ctl(**int** epfd, **int** op, **int** fd, **struct** epoll_event *event);    
**int** epoll_wait(**int** epfd, **struct** epoll_event *events,**int** maxevents, **int** timeout);  

우선 epoll 호출create 에서 epoll 대상 을 만 듭 니 다.매개 변수 size 는 커 널 이 정확하게 처리 할 수 있 는 최대 문형 수 입 니 다. 이 최대 수 보다 많 을 때 커 널 은 효 과 를 보장 하지 않 습 니 다.
epoll_ctl 은 위 에 세 워 진 epoll 을 조작 할 수 있 습 니 다. 예 를 들 어 방금 만 든 socket 을 epoll 에 추가 하여 모니터링 하거나 epoll 이 모니터링 하고 있 는 어떤 socket 핸들 을 epoll 에서 옮 기 고 더 이상 모니터링 하지 않 는 등 입 니 다.
epoll_wait 호출 시 주어진 timeout 시간 내 에 모니터링 하 는 모든 핸들 에서 이벤트 가 발생 하면 사용자 상태 로 돌아 갑 니 다.
그렇다면 epoll 은 어떻게 이런 생각 을 이 루 었 을 까?
어떤 프로 세 스 가 epoll 을 호출 할 때creat 방법 을 사용 할 때 Liux 커 널 은 이벤트 poll 구조 체 를 만 듭 니 다. 이 구조 체 에는 두 구성원 의 사용 이 epoll 의 사용 방식 과 밀접 한 관 계 를 가지 고 있 습 니 다.
**struct** eventpoll {  

 //       ,            epoll    ,     epoll     。  

    **struct** rb_root rbr;  

//    rdllist       epoll_wait      、       。  

    **struct** list_head rdllist;  

}  

epoll 왜 이렇게 효율 적 입 니까?
우리 가 epoll 을 호출 할 때ctl 에 백만 개의 핸들 을 넣 었 을 때 epollwait 는 여전히 빠르게 돌아 갈 수 있 으 며, 이벤트 가 발생 한 핸들 을 사용자 에 게 효과적으로 줄 수 있 습 니 다.이것 은 우리 가 epoll 를 호출 하고 있 기 때문이다.create 시 커 널 은 epoll 파일 시스템 에 file 노드 를 만 드 는 것 을 제외 하고 커 널 cache 에 빨 간 검 은 나 무 를 만들어 서 나중에 epoll 을 저장 합 니 다.ctl 에서 들 려 오 는 socket 외 에 list 링크 를 하나 더 만들어 준 비 된 이 벤트 를 저장 합 니 다. epollwait 호출 시 이 list 링크 에 데이터 가 있 는 지 관찰 하면 됩 니 다.데이터 가 있 으 면 되 돌아 오고 데이터 가 없 으 면 sleep 입 니 다. timeout 시간 이 되면 링크 에 데이터 가 없어 도 되 돌아 갑 니 다.그래서 epollwait 는 매우 효율 적 입 니 다.
그리고 통상 적 으로 우리 가 백만 계 의 핸들 을 감시 해 야 하 더 라 도 대부분 한 번 에 아주 적은 양의 준비 완료 핸들 만 되 돌려 주기 때문에 epollwait 는 커 널 상태 copy 의 소량의 구문 에서 사용자 상태 까지 만 필요 합 니 다. 어떻게 효율 적 이지 않 을 수 있 습 니까?!
그럼 이 준비 완료 list 링크 는 어떻게 유지 되 나 요?우리 가 epoll 을 실행 할 때ctl 에 서 는 epoll 파일 시스템 에 있 는 file 대상 에 대응 하 는 빨 간 검 은 트 리 에 socket 을 올 리 는 것 외 에 커 널 인 터 럽 트 처리 프로그램 에 리 셋 함 수 를 등록 하여 커 널 에 알려 줍 니 다. 이 핸들 이 중단 되면 준비 완료 list 링크 에 넣 으 라 고 합 니 다.그래서 하나의 socket 에 데이터 가 도착 하면 커 널 은 네트워크 카드 의 데 이 터 를 커 널 에 복사 한 후에 socket 을 준비 링크 에 삽입 합 니 다.
이렇게 해서 빨 간 검 은 나무 하나, 준비 되 어 있 는 문형 링크 하나, 소량의 커 널 cache 는 우리 에 게 크 고 보 내 는 socket 처리 문 제 를 해결 해 주 었 다.실행 epollcreate 시, 붉 은 검 은 나무 와 준비 링크 를 만 들 고 epoll 을 실행 합 니 다.ctl 시 socket 핸들 을 추가 하면 빨간색 과 검은색 트 리 에 존재 하 는 지 확인 하고 즉시 되 돌아 오 며 존재 하지 않 으 면 트 리 에 추가 한 다음 커 널 에 리 셋 함 수 를 등록 하여 인 터 럽 트 이벤트 가 발생 했 을 때 준비 되 어 있 는 링크 에 데 이 터 를 삽입 합 니 다.실행 epollwait 시 준 비 된 링크 의 데 이 터 를 즉시 되 돌려 주면 됩 니 다.
마지막 으로 epoll 만 의 두 가지 모델 인 LT 와 ET 를 살 펴 보 자.LT 와 ET 모드 를 막론하고 위 에서 말 한 절차 에 적용 된다.차이 점 은 LT 모드 에서 하나의 핸들 에 있 는 사건 이 한 번 에 처리 되 지 않 으 면 나중에 epoll 을 호출 합 니 다.wait 시 이 핸들 을 되 돌려 줍 니 다. ET 모드 는 첫 번 째 로 되 돌아 갑 니 다.
이 일 을 어떻게 했 지?socket 핸들 에 이벤트 가 있 을 때 커 널 은 이 핸들 을 위 에서 말 한 준비 완료 list 링크 에 삽입 합 니 다. 이때 우 리 는 epoll 을 호출 합 니 다.wait, 준 비 된 socket 을 사용자 상태 메모리 에 복사 한 다음 준 비 된 list 링크 를 비 웁 니 다. 마지막 으로 epollwait 가 한 가지 일 을 했 습 니 다. 이 socket 을 검사 하 는 것 입 니 다. ET 모드 (LT 모드 의 핸들 입 니 다) 가 아니라면 이 socket 에 처리 되 지 않 은 이벤트 가 있 을 때 이 핸들 을 방금 비 운 준비 링크 로 돌려 놓 았 습 니 다.그래서 ET 의 문형 이 아 닙 니 다. 그 위 에 사건 이 있다 면 epollwait 는 매번 돌아온다.ET 모드 의 핸들 은 새로 중단 되 지 않 는 한 socket 의 이벤트 가 처리 되 지 않 았 더 라 도 epoll 에서 두 번 다시 중단 되 지 않 습 니 다.wait 에서 돌 아 왔 습 니 다.
epoll 의 장점:
1. 프로 세 스 가 많은 소켓 설명 자 를 여 는 것 을 지원 합 니 다 (FD)
select                FD       , FD_SETSIZE  ,    2048。                IM          。                       ,                     ,              (    Apache  ),    linux            ,         ,                     ,            。   epoll       ,     FD              ,         2048,    , 1GB         10   ,      cat

/ proc / sys / fs / file - max 를 살 펴 보면 일반적으로 이 수 는 시스템 메모리 와 매우 큰 관 계 를 가진다.
2. IO 효율 은 FD 수량 증가 에 따라 선형 으로 떨어진다.
   select/poll                  socket  ,        ,         socket "  " ,  select/poll               ,          。  epoll       ,    "  " socket    ---          epoll     fd   callback     。  ,  "  " socket         callback  ,  idle  socket   ,    ,epoll     " "AIO,         os  。    benchmark ,     socket        ---      LAN  ,epoll   select/poll     ,  ,      epoll_ctl,           。      idle

connections 가 WAN 환경 을 모 의 하면 epoll 의 효율 은 select / poll 보다 훨씬 높다.
3. mmap 를 사용 하여 커 널 과 사용자 공간의 메시지 전달 을 가속 화 합 니 다.
        epoll      。   select,poll  epoll      FD         ,                ,    ,epoll          mmap        。         2.5     epoll  ,         mmap    。

4. 커 널 미세 조정
이 점 은 사실 epoll 의 장점 이 아니 라 전체 Liux 플랫폼 의 장점 입 니 다.Liux 플랫폼 을 의심 할 수 있 지만 Liux 플랫폼 이 커 널 을 미세 조정 하 는 능력 을 부여 하 는 것 을 피 할 수 없습니다.예 를 들 어 커 널 TCP / IP 프로 토 콜 스 택 은 메모리 탱크 관리 sk 를 사용 합 니 다.buff 구조, 그러면 실행 시기 에 이 메모리 pool (skb head pool) 의 크기 를 동적 으로 조정 할 수 있 습 니 다. echo XXXX > / proc / sys / net / core / hotlist_length 완성.예 를 들 어 listen 함수 의 두 번 째 매개 변수 (TCP 가 악 수 를 3 번 하 는 패 킷 대기 열 길이) 도 플랫폼 메모리 크기 에 따라 동적 으로 조정 할 수 있 습 니 다.심지어 하나의 패 킷 의 수량 이 많 지만 모든 패 킷 자체 의 크기 가 작은 특수 시스템 에서 최신 NAPI 네트워크 카드 구동 구 조 를 시도 합 니 다.
http://blog.csdn.net/mmshixing/article/details/51848673

좋은 웹페이지 즐겨찾기