Книга: Основы программирования в Linux

Ведение системных журналов

Ведение системных журналов

Многие приложения нуждаются в регистрации своей деятельности. Системные программы очень часто выводят сообщения на консоль или записывают их в регистрационный системный журнал. В этих сообщениях могут регистрироваться ошибки, предупреждения или более общая информация о состоянии системы. Например, программа su может зафиксировать тот факт, что пользователь пытался получить привилегии супер пользователя и потерпел неудачу.

Очень часто зарегистрированные сообщения записываются в системные файлы в каталоге, предоставляемом для этой цели. Это может быть каталог /usr/admor/var/log. При типичной установке ОС Linux все системные сообщения содержатся в файле /var/log/messages, в файл /var/log/mail включены другие регистрируемые сообщения от почтовой системы, а в файле /var/log/debug могут храниться отладочные сообщения. Проверить конфигурацию своей системы можно в файле /etc/syslog.conf или /etc/syslog-ng/syslog-ng.conf в зависимости от версии Linux.

Далее приведены некоторые примеры зарегистрированных сообщений.

Mar 2 6 18:25:51 suse103 ifstatus: eth0 device: Advanced Micro Devices [AMD] 79c970 [PCnet32 LANCE] (rev 10)
Mar 26 18:25:51 suse103 ifstatus: eth0 configuration: eth-id-00:0c:29:0e:91:72
...
May 20 06:56:56 suse103 SuSEfirewall2: Setting up rules from /etc/sysconfig/SuSEfirewall2
...
May 20 06:56:57 suse103 SuSEfirewall2: batch committing
...
May 20 06:56:57 suse103 SuSEfirewall2: Firewall rules successfully set
...
Jun 9 09:11:14 suse103 su: (to root) neil on /dev/pts/18 09:50:35

В этом выводе показаны виды регистрируемых сообщений. Несколько первых отправлены непосредственно ядром Linux во время его загрузки и обнаружения установленного оборудования. Брандмауэр сообщает о своей перенастройке. И наконец, программа su извещает о том, что доступ с учетной записью суперпользователя получен пользователем neil.

Примечание

Для просмотра регистрируемых сообщений вы можете запросить права суперпользователя.

Некоторые системы UNIX не предоставляют файлов с удобными для чтения сообщениями, но они снабжают администраторов средствами для чтения базы данных системных событий. См. подробности в системной документации.

Несмотря на то, что формат и хранение системных сообщений могут отличаться, метод формирования сообщений стандартный. В спецификации UNIX представлен доступный всем программам интерфейс формирования регистрируемых сообщений с помощью функции syslog.

#include <syslog.h>
void syslog(int priority, const char *message, arguments...);

Функция syslog посылает регистрируемое сообщение средству ведения системного журнала (logging facility). У каждого сообщения есть аргумент priority, полученный поразрядной операцией OR из степени важности сообщения (severity level) и типа программы, формирующей сообщение (facility value). Степень важности определяет необходимые действия, а тип программы фиксирует инициатора сообщения.

Типы программ (из файла syslog.h) включают константу LOG_USER, применяемую для обозначения сообщения, пришедшего из приложения пользователя (по умолчанию), и константы LOG_LOCAL0, LOG_LOCAL1, ..., LOG_LOCAL7, зарезервированные для локального администратора.

В табл. 4.6 перечислены степени важности сообщений в порядке убывания приоритета.

Таблица 4.6

Приоритет Описание
LOG_EMERG Кризисная ситуация
LOG_ALERT Проблема с высоким приоритетом, например, повреждение базы данных
LOG_CRIT Критическая ошибка, например, повреждение оборудования
LOG_ERR Ошибки
LOG_WARNING Предупреждение
LOG_NOTICE Особые обстоятельства, требующие повышенного внимания
LOG_INFO Информационные сообщения
LOG_DEBUG Отладочные сообщения

В зависимости от настройки системы сообщения типа LOG_EMER могут пересылаться всем пользователям системы, сообщения LOG_ALERT могут отправляться по электронной почте администратору, сообщения LOG_DEBUG могут игнорироваться, а сообщения других типов могут записываться в файл. Вы можете написать программу, которая применяет средство регистрации сообщений, просто вызывая функцию syslog, когда вы хотите создать регистрируемое сообщение.

У сообщения, создаваемого syslog, есть заголовок и тело сообщения. Заголовок создается из индикатора типа программы, формирующей сообщение, и даты и времени. Тело сообщения создается из параметра message, передаваемого функции syslog, который действует как строка format функции printf. Остальные аргументы syslog используются в соответствии со спецификаторами преобразований в стиле функции printf, заданными в строке message. Дополнительно может применяться спецификатор %m для включения строки сообщения об ошибке, ассоциированной с текущим значением переменной errno. Эта возможность может оказаться полезной для регистрации сообщений об ошибках.

Выполните упражнение 4.13.

Упражнение 4.13. Применение функции syslog

В этой программе осуществляется попытка открыть несуществующий файл.

#include <syslog.h>
#include <stdio.h>
#include <stdlib.h>
int main() {
 FILE *f;
 f = fopen("not_here", "r");
 if (!f) syslog(LOG_ERR|LOG_USER, "oops - %mn");
 exit(0);
}

Когда вы откомпилируете и выполните программу syslog.с, то не увидите никакого вывода, но в конце файла /var/log/messages теперь содержится следующая строка:

Jun 9 09:24:50 suse103 syslog: oops — No such file or directory

Как это работает

В данной программе вы пытаетесь открыть файл, которого нет. Когда попытка заканчивается неудачно, вы вызываете функцию syslog для записи случившегося в системный журнал.

Обратите внимание на то, что регистрируемое сообщение не указывает, какая программа вызвала средство регистрации; оно просто констатирует тот факт, что была вызвана функция syslog с сообщением. Спецификатор преобразования %m был заменен описанием ошибки, в данном случае сообщающим об отсутствии файла. Это гораздо полезнее, чем простой отчет, содержащий внутренний номер ошибки.

В файле syslog.h определены и другие функции, применяемые для изменения поведения средств ведения системных журналов.

К ним относятся следующие функции:

#include <syslog.h> void closelog(void);
void openlog(const char *ident, int logopt, int facility);
int setlogmask(int maskpri);

Вы можете изменить способ представления ваших регистрируемых сообщений, вызвав функцию openlog. Это позволит задать строку ident, которая будет добавляться к вашим регистрируемым сообщениям. Вы можете применять ее для индикации программы, создавшей сообщение. Параметр facility записывает текущий принятый по умолчанию тип программы, формирующей сообщение, который будет использоваться в последующих вызовах syslog. По умолчанию устанавливается значение LOG_USER. Параметр logopt настраивает поведение будущих вызовов функции syslog. Он представляет собой результат поразрядной операции OR нулевого или большего числа параметров, приведенных в табл. 4.7.

Таблица 4.7

Параметр logopt Описание
LOG_PID Включает в сообщения идентификатор процесса, уникальный номер, выделяемый системой каждому процессу
LOG_CONS Посылает сообщения на консоль, если они не могут быть записаны
LOG_ODELAY Открывает средство регистрации сообщений при первом вызове функции syslog
LOG_NDELAY Открывает средство регистрации сообщений немедленно, не дожидаясь первого регистрируемого сообщения

Функция openlog выделит и откроет дескриптор файла, который будет применяться для записи в программе ведения системного журнала. Вы сможете закрыть его, вызвав функцию closelog. Имейте в виду, что вам не нужно вызывать функцию openlog перед вызовом syslog, потому что последняя при необходимости самостоятельно откроет средство ведения системного журнала.

Вы можете управлять приоритетом регистрируемых вами сообщений с помощью установки маски регистрации, используя функцию setlogmask. Все будущие вызовы syslog с разными приоритетами, не заданными в маске регистрации, будут отброшены, таким образом, вы сможете, например, использовать маску для отключения сообщений типа LOG_DEBUG без необходимости изменять тело программы.

Вы можете создать маску для регистрируемых сообщений, используя значение LOG_MASK(priority), создающее маску только для одного приоритета, или значение LOG_UPTO(priority), создающее маску для всех приоритетов вплоть до заданного.

Выполните упражнение 4.14.

Упражнение 4.14. Маска регистрации (logmask)

В этом примере вы увидите logmask в действии.

#include <syslog.h>
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
int main() {
 int logmask;
 openlog("logmask", LOG_PID|LOG_CONS, LOG_USER);
 syslog(LOG_INFO, "informative message, pid = %d", getpid());
 syslog(LOG_DEBUG, "debug message, should appear");
 logmask = setlogmask(LOG_UPTO(LOG_NOTICE));
 syslog(LOG_DEBUG, "debug message, should not appear");
exit(0);
}

Программа logmask.c ничего не выводит, но в типичной системе Linux вы увидите в файле /var/log/messages, ближе к концу, следующую строку:

Jun 9 09:28:52 suse103 logmask[19339] : informative message, pid = 19339

Файл, настроенный на получение регистрируемых сообщений об отладке (в зависимости от настройки регистрации, это чаще всего файл /var/log/debug или иногда файл /var/log/messages), должен содержать следующую строку:

Jun 9 09:28:52 susel03 logmask[19339]: debug message, should appear

Как это работает

Программа инициализирует средство ведения системного журнала, названное logmask, и запрашивает включение идентификатора процесса в регистрируемые сообщения. Информирующее сообщение записывается в файл /var/log/messages, а отладочное сообщение — в файл /var/log/debug. Второе отладочное сообщение не появляется, потому что вы вызвали функцию setlogmask с игнорированием всех сообщений с приоритетом ниже LOG_NOTICE. (Учтите, что этот метод не работает в ранних вариантах ядра Linux.)

Если в установленную у вас систему не включена регистрация отладочных сообщений или она настроена иначе, отладочные сообщения могут не появляться. Для разблокирования всех отладочных сообщений и для получения подробностей настройки см. системную документацию, посвященную функции syslog или syslog-ng.

Программа logmask.c также использует функцию getpid, которая, наряду с тесно связанной с ней функцией getppid, определена следующим образом:

#include <sys/types.h>
#include <unistd.h>
pid_t getpid(void);pid_t getppid(void);

Функции возвращают идентификаторы вызвавшего и родительского процессов. Дополнительную информацию об идентификаторах процессов (PID) см. в главе 11.

Оглавление книги


Генерация: 1.119. Запросов К БД/Cache: 3 / 1
поделиться
Вверх Вниз