Tại sao scp rất chậm và làm thế nào để làm cho nó nhanh hơn?


59

Tôi đang cố gắng sao chép một loạt các tệp với scpnhưng nó rất chậm. Đây là một ví dụ với 10 tệp:

$ time scp cap_* user@host:~/dir
cap_20151023T113018_704979707.png    100%  413KB 413.2KB/s   00:00    
cap_20151023T113019_999990226.png    100%  413KB 412.6KB/s   00:00    
cap_20151023T113020_649251955.png    100%  417KB 416.8KB/s   00:00    
cap_20151023T113021_284028464.png    100%  417KB 416.8KB/s   00:00    
cap_20151023T113021_927950468.png    100%  413KB 413.0KB/s   00:00    
cap_20151023T113022_567641507.png    100%  413KB 413.1KB/s   00:00    
cap_20151023T113023_203534753.png    100%  414KB 413.5KB/s   00:00    
cap_20151023T113023_855350640.png    100%  412KB 411.7KB/s   00:00    
cap_20151023T113024_496387641.png    100%  412KB 412.3KB/s   00:00    
cap_20151023T113025_138012848.png    100%  414KB 413.8KB/s   00:00    
cap_20151023T113025_778042791.png    100%  413KB 413.4KB/s   00:00    

real    0m43.932s
user    0m0.074s
sys 0m0.030s

Điều kỳ lạ là tốc độ truyền tải khoảng 413KB / giây và kích thước tệp khoảng 413KB nên thực sự cần truyền một tệp mỗi giây, tuy nhiên mất khoảng 4,3 giây cho mỗi tệp.

Bất kỳ ý tưởng mà chi phí này đến từ đâu, và có cách nào để làm cho nó nhanh hơn?


3
Tốc độ nào bạn mong đợi (nghĩa là có một giao thức khác cho thấy tốc độ truyền cao hơn giữa hai máy giống nhau)? Điều gì xảy ra khi bạn scp một tệp lớn hơn nhiều (có lẽ là sự kết hợp của tất cả các tệp 413KB của bạn)?
dhag

6
Có vẻ như hệ thống từ xa có thể đang cố gắng phân giải địa chỉ IP của máy khách thành tên và bạn phải chờ thời gian chờ trước khi phiên diễn ra. Bạn có thể điều tra sửa lỗi đó (ví dụ: thêm địa chỉ IP của bạn vào tệp / etc / hosts của đích).
wurtel

4
Điều đáng nói là cờ -C cho phép nén trong khi truyền. Mặc dù vấn đề của bạn có vẻ là chi phí bắt đầu chuyển, nhưng về cơ bản, nén là "miễn phí" và hầu như luôn luôn có ích.
Sam

@wurtel: Tôi không thấy những gì bạn đang thấy, tất cả những gì tôi thấy là thời gian. Dù sao cũng chỉ nên có một cuộc gọi DNS ngược duy nhất.
James phục hồi Monica Polk

Bạn đang dựa vào SCP để bảo mật hay chỉ để sao chép từ xa?
Freiheit

Câu trả lời:


17

Nhận xét của @ wurtel có lẽ đúng: có rất nhiều chi phí thiết lập mỗi kết nối. Nếu bạn có thể khắc phục rằng bạn sẽ nhận được chuyển khoản nhanh hơn (và nếu bạn không thể, chỉ cần sử dụng rsynccách giải quyết của @ roaima ). Tôi đã thực hiện một thử nghiệm chuyển các tệp có kích thước tương tự ( head -c 417K /dev/urandom > foo.1và tạo một số bản sao của tệp đó) sang một máy chủ cần một thời gian để kết nối (HOST4) và một tệp phản hồi rất nhanh (HOST1):

$ time ssh $HOST1 echo


real    0m0.146s
user    0m0.016s
sys     0m0.008s
$ time scp * $HOST1:
foo.1                                         100%  417KB 417.0KB/s   00:00    
foo.2                                         100%  417KB 417.0KB/s   00:00    
foo.3                                         100%  417KB 417.0KB/s   00:00    
foo.4                                         100%  417KB 417.0KB/s   00:00    
foo.5                                         100%  417KB 417.0KB/s   00:00    

real    0m0.337s
user    0m0.032s
sys     0m0.016s
$ time ssh $HOST4 echo


real    0m1.369s
user    0m0.020s
sys     0m0.016s
$ time scp * $HOST4:
foo.1                                         100%  417KB 417.0KB/s   00:00    
foo.2                                         100%  417KB 417.0KB/s   00:00    
foo.3                                         100%  417KB 417.0KB/s   00:00    
foo.4                                         100%  417KB 417.0KB/s   00:00    
foo.5                                         100%  417KB 417.0KB/s   00:00    

real    0m6.489s
user    0m0.052s
sys     0m0.020s
$ 

1
Cảm ơn, điều đó rất thú vị. Đầu ra scp bị hỏng nếu hiển thị cùng thời điểm mặc dù nó hoàn toàn khác biệt giữa máy chủ này với máy chủ khác. Chúng có lẽ nên bao gồm thời gian kết nối trong tổng thời gian.
nguyệt quế

1
Vì vậy, giả thuyết của bạn là nó tạo ra một kết nối mới một lần cho mỗi tệp?
rogerdpack

59

Bạn có thể sử dụng rsync(kết thúc ssh), sử dụng một kết nối duy nhất để chuyển tất cả các tệp nguồn.

rsync -avP cap_* user@host:dir

Nếu bạn không có rsync(và tại sao không !?), bạn có thể sử dụng tarvới sshnhư thế này, mà tránh tạo ra một tập tin tạm thời:

tar czf - cap_* | ssh user@host tar xvzfC - dir

Điều rsyncnày được ưu tiên, tất cả những thứ khác đều bằng nhau, vì nó có thể khởi động lại trong trường hợp bị gián đoạn.


6
Bạn đang nói một lệnh scpgọi sẽ không sử dụng một kết nối duy nhất để chuyển tất cả các tệp?
một CVn

1
Trong trường hợp tarpipe, không cần cho f -mỗi bên, vì tar xuất ra / đọc từ stdout / stdin theo mặc định. Vì vậy, tar cz cap_* | ssh user@host tar xvzC dirsẽ làm điều đó.
run rẩy

1
@tremby không nhất thiết. tarcó thể được biên dịch với các giá trị mặc định khác nhau (xem tar --show-defaultsbạn có đang sử dụng GNU tar hay /etc/default/tarkhông, và trong cả hai trường hợp, đừng quên TAPEbiến môi trường)
roaima

1
@ MichaelKjorling ban đầu tôi đã giả định rằng scpsẽ tạo một kết nối mới cho mỗi tệp, nhưng theo hồi ức - và sau khi kiểm tra lại với tshark- tôi nhận ra rằng mình đã sai. Tại thời điểm này, tôi không còn chắc chắn lý do tại sao OP scpnên mất một thời gian dài như vậy cho mỗi tệp.
roaima

@roaima, thú vị, cảm ơn. Tôi chưa bao giờ nhận thấy stdin / stdout không được mặc định cho đến nay. BSD tar trên máy Mac của tôi tại nơi làm việc không đề cập đến một TAPE env var trong trang man của nó, mặc dù GNU tar trên máy Linux của tôi có.
run rẩy

15

Đó là cuộc đàm phán chuyển nhượng cần có thời gian. Nói chung, các hoạt động trên n tệp của b byte mỗi mất nhiều thời gian hơn nhiều so với một thao tác trên một tệp n * b byte. Điều này cũng đúng, ví dụ như đối với I / O đĩa.

Nếu bạn nhìn kỹ, bạn sẽ thấy tốc độ truyền trong trường hợp này là size_of_the_file / giây.

Để truyền tệp hiệu quả hơn, hãy kết hợp chúng lại với nhau tar, sau đó chuyển tarball:

tar cvf myarchive.tar cap_20151023T*.png

hoặc, nếu bạn cũng muốn nén kho lưu trữ,

tar cvzf myarchive.tar.gz myfile*

Có nén hay không phụ thuộc vào nội dung tập tin, vd. nếu chúng là JPEG hoặc PNG, nén sẽ không có hiệu lực.


PNG sử dụng def def, và gzipping chúng là vô nghĩa quá.
Arthur2e5

Tôi muốn nói rằng vì việc nén tar không có tác động tiêu cực khi các tập tin không thể được nén thêm nữa, đó là một cách tốt để đặt-z
Centimane

1
@Dave nếu chúng không thể được nén hoặc mạng nhanh, nó sẽ làm mọi thứ chậm lại.
Davidmh

@Davidmh điều này sẽ được một số lượng đáng kể mặc dù? Tôi nghĩ rằng việc nén một tệp đã được nén sẽ khá nhanh vì nó thực sự chỉ cần xem qua những gì nó có thể nén và thấy rằng nó không là gì cả. Tôi đoán nếu tarbình thường thực hiện vượt qua lần thứ hai để nén hoặc nếu nó sẽ nén và lưu trữ cùng một lúc
Centimane

3
@Dave trong trường hợp của tôi (dữ liệu trên HD hiện đại 7000 vòng / phút, CPU cao cấp, mạng rất nhanh, không hề khoe khoang), tar mà không nén hoàn toàn bị ràng buộc IO, nhưng với -zCPU bị ràng buộc và chậm hơn nhiều. gzip sẽ luôn cố gắng nén, do đó làm chậm; sau tất cả, bạn không thể biết liệu một chuỗi byte có thể nén được hay không cho đến khi bạn cố nén nó. Trong thiết lập của tôi, ngay cả khi truyền tệp văn bản đơn giản, rsync không nén là nhanh nhất theo hệ số 2-3 so với mức nén nhẹ nhất. Tất nhiên, YMMV.
Davidmh

6

Một lý do khác khiến scp chậm hơn so với yêu cầu, đặc biệt là trên các mạng băng thông cao, là nó có bộ đệm điều khiển luồng nội bộ được xác định tĩnh mà cuối cùng trở thành nút cổ chai hiệu năng mạng.

HPN-SSH là phiên bản vá của OpenSSH, giúp tăng kích thước của các bộ đệm này. Nó tạo ra sự khác biệt lớn đối với tốc độ truyền scp (xem biểu đồ trên trang web, nhưng tôi cũng nói từ kinh nghiệm cá nhân). Tất nhiên, để có được những lợi ích bạn cần cài đặt HPN-SSH trên tất cả các máy chủ của mình nhưng nó cũng đáng giá nếu bạn thường xuyên cần chuyển các tệp lớn xung quanh.


5

Tôi đã sử dụng kỹ thuật được mô tả ở đây sử dụng gzip và netcat song song để nhanh chóng nén và sao chép dữ liệu.

Nó đun sôi xuống:

# SOURCE: 
> tar -cf - /u02/databases/mydb/data_file-1.dbf | pigz | nc -l 8888

# TARGET:
> nc <source host> 8888 | pigz -d | tar xf - -C /

Điều này sử dụng tar để thu thập các tập tin hoặc tập tin. Sau đó sử dụng pigz để lấy nhiều luồng cpu để nén và gửi tệp, việc truyền mạng đang sử dụng netcat. Về phía bên nhận, netcat lắng nghe sau đó giải nén (song song) và gỡ bỏ.


3
nckhông được mã hóa. Thêm một số ssh -Dphép thuật có thể?
Arthur2e5

điều này thực sự khá tuyệt vời
Jabran Saeed

5

Chỉ có vấn đề này khi thực hiện chuyển từ trang này sang trang khác của một tệp mp4 lớn thông qua scp. Đã nhận được ~ 250KB / s. Sau khi vô hiệu hóa bảo vệ lũ UDP (FP) trên tường lửa đích, tốc độ truyền tăng lên 6,5MB / s. Khi bật lại FP, tốc độ giảm xuống ~ 250KB / s.

Người gửi: cygwin, Người nhận: Fedora 20, Tường lửa Sophos UTM.

SSH sử dụng UDP để làm gì? @ superuser.com - Nó không trực tiếp từ những gì tôi đọc.

Khi xem xét nhật ký tường lửa, phát hiện lũ đã xảy ra trên cả hai cổng nguồn & số 4500 trên các địa chỉ IP công cộng, chứ không phải các địa chỉ VPN nội bộ của trang web riêng tư. Vì vậy, có vẻ như vấn đề của tôi có thể là tình huống NAT Traversal trong đó scpdữ liệu TCP cuối cùng được mã hóa và gói gọn trong các gói ESP & UDP, và do đó phải tuân theo FP. Để loại bỏ scpkhỏi phương trình, tôi đã chạy một hoạt động sao chép tệp Windows trên VPN và nhận thấy hiệu suất tương tự scpvới và không bật FP. Cũng đã chạy iperfthử nghiệm qua TCP và nhận thấy 2Mbit / giây với FP và 55Mbits / giây mà không có.

NAT-T hoạt động với IPSec như thế nào? @ cisco.com

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.