Trong bài viết này, chúng ta sẽ khám phá bộ công cụ và môi trường ưu việt của GNU/Linux, giúp bạn tự tin giải quyết sự cố ngay trên những hệ thống mới lạ. Qua đó, bạn sẽ nắm bắt được các phương pháp khắc phục lỗi và tối ưu hóa hiệu suất hệ thống, một kỹ năng không thể thiếu cho chuyên gia IT hiện đại. DataOnline sẽ hướng dẫn bạn:
● Cách kiểm tra dung lượng đĩa
● Cách kiểm tra kích thước bộ nhớ
● Cách kiểm tra tải hệ thống
● Cách tìm và kết thúc tiến trình hệ thống
● Cách sử dụng log để tìm thông tin hỗ trợ khắc phục sự cố hệ thống
Yêu cầu phần mềm và các quy ước được sử dụng
Category | Requirements, Conventions or Software Version Used |
---|---|
System | Ubuntu 20.04, Fedora 31 |
Software | N/A |
Cần có quyền truy cập đặc quyền trên hệ thống Linux của bạn dưới dạng người dùng root hoặc thông qua lệnh sudo.
Quy ước
#
– yêu cầu các lệnh Linux được thực thi với đặc quyền root, có thể thực thi trực tiếp với tư cách người dùng root hoặc sử dụng lệnh sudo.$
– yêu cầu các lệnh Linux được thực thi với tư cách người dùng thường không có đặc quyền.
Giới thiệu
Mặc dù GNU/Linux được biết đến với tính ổn định và mạnh mẽ, nhưng vẫn có trường hợp xảy ra sự cố. Nguyên nhân của vấn đề có thể đến từ cả bên trong lẫn bên ngoài. Ví dụ, có thể có một tiến trình hoạt động sai khiến chiếm dụng tài nguyên, hoặc một ổ cứng cũ gặp lỗi, dẫn đến báo cáo lỗi I/O.
Dù nguyên nhân là gì, chúng ta cần biết phải tìm ở đâu và làm thế nào để thu thập thông tin về tình trạng hệ thống; hướng dẫn này cung cấp một cách tổng quát để xác định lỗi đã xảy ra. Việc giải quyết sự cố bắt đầu từ việc nắm bắt thông tin về vấn đề, tìm hiểu chi tiết, xác định nguyên nhân gốc rễ và từ đó khắc phục. Như với bất kỳ nhiệm vụ nào, GNU/Linux cung cấp vô số công cụ hỗ trợ tiến trình khắc phục sự cố. Một vài mẹo và phương pháp dưới đây là những ví dụ chung có thể áp dụng trên nhiều bản phân phối và phiên bản.
Triệu chứng
Giả sử chúng ta có một chiếc laptop tốt để làm việc. Máy đang chạy phiên bản Ubuntu, CentOS hoặc Red Hat Linux mới nhất, với các bản cập nhật luôn được cài đặt để duy trì mọi thứ luôn mới mẻ. Chiếc laptop này được sử dụng cho công việc hàng ngày: xử lý email, trò chuyện, lướt web, có thể tạo một vài bảng tính, v.v. Không có phần mềm đặc biệt nào được cài đặt ngoài bộ Office, trình duyệt, ứng dụng email, v.v. Từ ngày này sang ngày khác, đột nhiên máy tính trở nên cực kỳ chậm chạp. Chúng ta đã làm việc trên đó khoảng một giờ đồng hồ, vì vậy lỗi khởi động không phải là nguyên nhân. Vậy chuyện gì đang xảy ra…?
Kiểm tra tài nguyên hệ thống
GNU/Linux không trở nên chậm chạp nếu không có nguyên nhân. Hệ thống sẽ cho ta biết nguồn gốc vấn đề, miễn là nó có thể trả lời. Giống như bất kỳ chương trình nào đang chạy trên máy tính, hệ điều hành sử dụng tài nguyên hệ thống và khi số lượng tài nguyên có hạn, các tác vụ phải chờ đến khi đủ tài nguyên để thực hiện. Điều này sẽ làm cho các phản hồi chậm dần lại. Vì vậy, khi có sự cố, việc kiểm tra trạng thái tài nguyên hệ thống luôn là bước hữu ích. Nói chung, tài nguyên hệ thống (trong máy cục bộ) của chúng ta bao gồm đĩa, bộ nhớ và CPU. Hãy cùng kiểm tra tất cả.
Dung lượng đĩa
Nếu hệ điều hành đang chạy không còn đủ dung lượng đĩa, đó là tin xấu. Vì các dịch vụ đang chạy không thể ghi các tập tin log, chúng có thể bị treo (crash) nếu đang hoạt động hoặc không khởi động được nếu đĩa đã đầy. Ngoài các tập tin log, các socket và tập tin PID (Process IDentifier) cũng cần được ghi vào đĩa, và mặc dù chúng có kích thước nhỏ, nhưng nếu không còn chỗ, chúng sẽ không được tạo ra.
Để kiểm tra dung lượng đĩa khả dụng, chúng ta có thể sử dụng lệnh df
trong terminal và thêm tham số -h
để xem kết quả được làm tròn theo Megabyte và Gigabyte. Đối với chúng ta, mục cần quan tâm là những volume có phần trăm sử dụng (Use%) đạt 100%. Điều này có nghĩa là volume đó đã đầy. Ví dụ xuất ra dưới đây cho thấy chúng ta có đủ dung lượng đĩa:
$ df -h Filesystem Size Used Avail Use% Mounted on devtmpfs 1.8G 0 1.8G 0% /dev tmpfs 1.8G 0 1.8G 0% /dev/shm tmpfs 1.8G 1.3M 1.8G 1% /run /dev/mapper/lv-root 49G 11G 36G 24% / tmpfs 1.8G 0 1.8G 0% /tmp /dev/sda2 976M 261M 649M 29% /boot /dev/mapper/lv-home 173G 18G 147G 11% /home tmpfs 361M 4.0K 361M 1% /run/user/1000
Vậy là chúng ta có đủ không gian trên các ổ đĩa. Lưu ý rằng trong trường hợp của chiếc laptop chậm, việc đầy đĩa không có khả năng là nguyên nhân gốc rễ. Khi đĩa đầy, các chương trình thường bị treo hoặc không khởi động được ngay từ đầu; trong trường hợp cực đoan, thậm chí cả đăng nhập cũng thất bại sau khi khởi động.
Bộ Nhớ
Bộ nhớ là một tài nguyên quan trọng; nếu thiếu bộ nhớ, hệ điều hành có thể phải ghi tạm thời một số phần không sử dụng của bộ nhớ xuống đĩa (được gọi là “swap out”) để giải phóng bộ nhớ cho tiến trình tiếp theo, rồi đọc lại khi tiến trình đó cần. Phương pháp này gọi là swapping và chắc chắn sẽ làm hệ thống chậm lại, vì việc ghi và đọc dữ liệu từ đĩa chậm hơn nhiều so với xử lý trong RAM.
Để kiểm tra mức sử dụng bộ nhớ, chúng ta có lệnh tiện dụng free
và có thể thêm tham số để xem kết quả theo đơn vị Megabyte (-m
) hoặc Gigabyte (-g
):
$ free -m total used free shared buff/cache available Mem: 7886 3509 1547 1231 2829 2852 Swap: 8015 0 8015
Trong ví dụ trên, chúng ta có 8 GB bộ nhớ, trong đó 1,5 GB còn trống và khoảng 3 GB được sử dụng cho bộ nhớ cache. Lệnh free
cũng cho biết trạng thái của swap: trong trường hợp này, swap hoàn toàn trống, nghĩa là kể từ khi khởi động, hệ điều hành chưa cần phải ghi bất kỳ nội dung bộ nhớ nào xuống đĩa, ngay cả khi tải đỉnh. Điều này thường có nghĩa là chúng ta có nhiều bộ nhớ hơn mức sử dụng thực tế. Vậy nên, về mặt bộ nhớ, tình hình của chúng ta vẫn tốt, có đủ tài nguyên cần thiết.
Tải hệ thống
CPU là bộ phận thực hiện các phép tính; nếu thiếu thời gian xử lý của CPU, hệ thống có thể trở nên chậm lại. Các phép tính cần thiết sẽ phải chờ đợi cho tới khi có CPU rảnh để xử lý. Cách đơn giản nhất để xem tải của CPU là sử dụng lệnh uptime
:
$ uptime 12:18:24 up 4:19, 8 users, load average: 4,33, 2,28, 1,37
Ba con số sau “load average” tương ứng với mức tải trung bình trong 1, 5 và 15 phút qua. Trong ví dụ này, máy có 4 lõi CPU, nhưng hệ thống đang sử dụng vượt quá khả năng thực tế của máy. Ngoài ra, các giá trị lịch sử cho thấy tải hệ thống đã tăng đáng kể trong vài phút vừa qua. Có lẽ chúng ta đã tìm ra được nguyên nhân gây ra sự cố?
Các tiến trình tiêu thụ nhiều tài nguyên
Hãy cùng xem toàn cảnh về việc tiêu thụ CPU và bộ nhớ, với các tiến trình hàng đầu sử dụng các tài nguyên này. Chúng ta có thể chạy lệnh top
để xem tải hệ thống (gần như theo thời gian thực):
- Dòng đầu tiên của
top
tương đương với kết quả của lệnhuptime
. - Tiếp theo, chúng ta thấy số lượng tiến trình đang chạy, ngủ, v.v. Lưu ý số lượng các tiến trình “zombie” (tiến trình đã chết nhưng chưa được giải phóng); trường hợp này là 0, nhưng nếu có tiến trình zombie thì cần được kiểm tra.
- Dòng tiếp theo hiển thị mức tải CPU theo phần trăm và phần trăm các hoạt động cụ thể mà CPU đang thực hiện. Ở đây, chúng ta thấy CPU đang bận phục vụ các chương trình ở không gian người dùng.
- Sau đó là hai dòng có nội dung tương tự như đầu ra của lệnh
free
, thể hiện mức sử dụng bộ nhớ của hệ thống. - Ở dưới đó là danh sách các tiến trình tiêu thụ nhiều tài nguyên nhất, được sắp xếp theo mức sử dụng CPU. Từ đó, chúng ta có thể xác định tiến trình nào đang “ăn” tài nguyên CPU; trong ví dụ này, đó là Firefox.
Kiểm tra các tiến trình
Làm sao tôi biết được rằng, vì tiến trình tiêu thụ nhiều tài nguyên nhất hiển thị là “Web Content” trong kết quả của top
? Bằng cách sử dụng lệnh ps
để truy vấn bảng tiến trình, dựa vào PID được hiển thị bên cạnh tiến trình đó, trong trường hợp này là 5785:
$ ps -ef| grep 5785 | grep -v "grep" sandmann 5785 2528 19 18:18 tty2 00:00:54 /usr/lib/firefox/firefox -contentproc -childID 13 -isForBrowser -prefsLen 9825 -prefMapSize 226230 -parentBuildID 20200720193547 -appdir /usr/lib/firefox/browser 2528 true tab
Với bước này, chúng ta đã tìm ra nguyên nhân gốc rễ của sự cố: Firefox đang chiếm dụng tài nguyên CPU đến mức hệ thống trở nên chậm chạp. Điều này không nhất thiết là lỗi của trình duyệt, bởi vì Firefox được thiết kế để hiển thị các trang web: chỉ để minh họa vấn đề về CPU, tôi đã mở hàng chục tab của một trang thử nghiệm căng thẳng (stress test) đến mức thiếu hụt CPU bộc lộ. Vậy nên, tôi không nên đổ lỗi cho trình duyệt mà phải trách bản thân vì đã mở quá nhiều trang tiêu thụ tài nguyên cùng lúc. Bằng cách đóng bớt một số tab, mức sử dụng CPU trở lại bình thường.
Kiểm tra các tiến trình
Vấn đề và giải pháp đã được nêu trên, nhưng điều gì sẽ xảy ra nếu tôi không thể truy cập trình duyệt để đóng một số tab? Giả sử phiên làm việc giao diện đồ họa bị khóa và tôi không thể đăng nhập lại, hoặc một tiến trình chạy “ngoài kiểm soát” không có giao diện cho phép thay đổi hành vi của nó? Trong trường hợp này, chúng ta có thể buộc hệ điều hành kết thúc tiến trình đó. Chúng ta đã biết PID của tiến trình “nổi loạn” từ lệnh ps
, và có thể sử dụng lệnh kill
để kết thúc nó:
$ kill 5785
Các tiến trình hoạt động đúng cách sẽ tự thoát ra, nhưng nếu không, thêm tham số -9
(lưu ý: “-9” là một tham số, không phải là từ “flag”) sẽ buộc tiến trình dừng:
$ kill -9 5785
Tuy nhiên, lưu ý rằng cách này có thể gây mất dữ liệu, bởi vì tiến trình không có thời gian để đóng các tập tin mở hoặc hoàn tất việc ghi kết quả xuống đĩa. Nhưng trong trường hợp của một tác vụ có thể lặp lại, sự ổn định của hệ thống có thể được ưu tiên hơn việc mất một số kết quả.
Tìm kiếm thông tin liên quan
Không phải lúc nào cũng có giao diện điều khiển cho các tiến trình; nhiều ứng dụng chỉ có các lệnh cơ bản kiểm soát hành vi của chúng – chẳng hạn như start, stop, reload,… bởi vì hoạt động nội bộ của chúng được quy định bởi cấu hình. Ví dụ trên thuộc dạng desktop, bây giờ hãy cùng xem một ví dụ phía máy chủ, khi gặp sự cố với máy chủ web.
Giả sử chúng ta có một máy chủ web phục vụ nội dung cho người dùng. Với số lượng truy cập lớn, việc nhận thông báo rằng dịch vụ không khả dụng là điều không hay. Ta có thể kiểm tra trang web trên trình duyệt chỉ để nhận được thông báo “unable to connect” (không thể kết nối). Vậy hãy kiểm tra máy chủ của dịch vụ web đó!
Kiểm tra các tập tin log
Máy chủ web của chúng ta chạy trên một hệ thống Fedora. Điều này quan trọng bởi vì các đường dẫn tập tin hệ thống phải được theo dõi. Fedora và tất cả các biến thể của Red Hat lưu trữ các tập tin log của máy chủ Apache tại đường dẫn /var/log/httpd
. Tại đây, ta có thể dùng lệnh view
để kiểm tra tập tin error_log
, nhưng có thể không tìm thấy thông tin liên quan đến vấn đề. Kiểm tra các tập tin log truy cập (access log
) cũng ban đầu không hiện ra vấn đề gì, nhưng suy nghĩ kỹ lại sẽ cho ta gợi ý: trên một máy chủ web có lượng truy cập ổn định, các mục cuối cùng của log truy cập nên rất gần với thời điểm hiện tại, nhưng mục cuối cùng lại cách đây đã một giờ. Kinh nghiệm cho thấy trang web luôn có khách ghé thăm mỗi phút.
Systemd
Cài đặt Fedora của chúng ta sử dụng systemd làm hệ thống init. Hãy truy vấn một số thông tin về máy chủ web với lệnh:
# systemctl status httpd ● httpd.service - The Apache HTTP Server Loaded: loaded (/usr/lib/systemd/system/httpd.service; disabled; vendor preset: disabled) Drop-In: /usr/lib/systemd/system/httpd.service.d └─php-fpm.conf Active: failed (Result: signal) since Sun 2020-08-02 19:03:21 CEST; 3min 5s ago Docs: man:httpd.service(8) Process: 29457 ExecStart=/usr/sbin/httpd $OPTIONS -DFOREGROUND (code=killed, signal=KILL) Main PID: 29457 (code=killed, signal=KILL) Status: "Total requests: 0; Idle/Busy workers 100/0;Requests/sec: 0; Bytes served/sec: 0 B/sec" CPU: 74ms aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29665 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29666 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29667 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29668 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29669 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29670 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29671 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29672 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Killing process 29673 (n/a) with signal SIGKILL. aug 02 19:03:21 mywebserver1.foobar systemd[1]: httpd.service: Failed with result 'signal'.
Ví dụ trên là một trường hợp đơn giản, khi tiến trình chính của Apache bị dừng do nhận tín hiệu KILL. Có thể có một quản trị viên khác có đặc quyền để thực hiện hành động này, vì vậy ta có thể kiểm tra ai đã đăng nhập (hoặc đã đăng nhập vào thời điểm máy chủ web bị dừng một cách mạnh mẽ) và hỏi họ về sự cố; nếu dịch vụ được dừng một cách tinh vi hơn, sẽ có lý do cụ thể đằng sau hành động đó. Nếu chỉ có chúng ta là quản trị viên duy nhất trên máy chủ, ta có thể kiểm tra nguồn gốc của tín hiệu đó – có thể xảy ra sự cố an ninh, hoặc hệ điều hành đã gửi tín hiệu kill. Trong cả hai trường hợp, ta có thể dùng các tập tin log của máy chủ, vì các đăng nhập SSH được ghi vào các tập tin log bảo mật (trong trường hợp của Fedora là /var/log/secure
), và cũng có các mục audit trong tập tin log chính (ở đây là /var/log/messages
). Có một mục ghi nhận lại những gì đã xảy ra ở phần cuối:
Aug 2 19:03:21 mywebserver1.foobar audit[1]: SERVICE_STOP pid=1 uid=0 auid=4294967295 ses=4294967295 msg='unit=httpd comm="systemd" exe="/usr/lib/systemd/systemd" hostname=? addr=? terminal=? res=failed'
Kết luận
Trong ví dụ minh họa này, tôi đã chủ động dừng tiến trình chính của máy chủ web trong phòng thí nghiệm để cho thấy cách xử lý sự cố một cách nhanh nhất. Khi gặp rắc rối liên quan đến máy chủ, phương pháp tối ưu là kiểm tra các tập tin log và tra cứu trạng thái các tiến trình đang chạy – hoặc việc thiếu hụt tiến trình – để nhanh chóng xác định nguyên nhân gốc rễ của vấn đề. Để làm được điều này hiệu quả, bạn cần hiểu rõ về các dịch vụ hoạt động trên hệ thống: biết rõ nơi lưu trữ log, cách truy cập thông tin về trạng thái của chúng, cũng như nhận thức được những giá trị thông thường được ghi nhận trong quá trình vận hành. Việc nắm bắt sớm các dấu hiệu bất thường không chỉ giúp phát hiện lỗi kịp thời mà còn ngăn ngừa sự cố leo thang.
Ngoài ra, có vô số công cụ hỗ trợ tự động hóa các quy trình này, như hệ thống giám sát (monitoring subsystem) và các giải pháp tổng hợp log, nhưng tất cả đều khởi nguồn từ kiến thức và kỹ năng của chính các quản trị viên IT. Việc nắm vững cách thức hoạt động của các dịch vụ, biết được cần kiểm tra những yếu tố nào để đảm bảo hệ thống vận hành ổn định, là chìa khóa để xây dựng kỹ năng khắc phục sự cố trên GNU/Linux, ngay cả khi làm việc với những máy chủ chưa quen thuộc.