Linux中使用syslog进行日志的打印

对于一个从单片机开发转向操作系统中的应用程序开发的攻城狮来说,对程序的调试方法的转换也是非常重要的。单片机的开发,一般使用jlink进行单步调试较多,但是对于在操作系统上进行应用程序一般都是比较庞大的,所以再使用单片机开发的调试思维就不现实啦。最常见的就是使用printf打印与syslog日志打印,对于printf的使用比较简单,所以这里主要介绍一下syslog的用法。

syslog的调试信息的打印是后台运行的,不占用控制台。并且可以进行调试信息级别的控制,这样可以避免输出很多无用的信息,让观看者可以更快的找到希望看到的信息。

函数介绍

对于linux系统中提供的日志打印服务,提供了一些库函数,一般使用的就是三个,openlog()、syslog()、closelog()

       #include <syslog.h>

       void openlog(const char *ident, int option, int facility);
       void syslog(int priority, const char *format, ...);
       void closelog(void);

 void openlog(const char *ident, int option, int facility);  用于打开系统记录

  • ident   指向的字符串可以是想要打出的任意字符,它所表示的字符串将固定地加在每行日志的前面以标识这个日志,该标志通常设置为程序的名称。
  • .option  参数所指定的标志用来控制openlog()操作和syslog()的后续调用。他的值为具体是下列值取或运算的结果

LOG_CONS
直接写入系统控制台,如果有一个错误,同时发送到系统日志记录。
LOG_NDELAY
立即打开连接(通常,打开连接时记录的第一条消息)。
LOG_NOWAIT
不要等待子进程,因为其有可能在记录消息的时候就被创建了(GNU C库不创建子进程,所以该选项在Linux上没有影响。)
LOG_ODELAY
延迟连接的打开直到syslog函数调用。(这是默认情况下,需要没被指定的情况下。)
LOG_PERROR
(不在SUSv3情况下)同时输出到stderr(标准错误文件)。
LOG_PID
包括每个消息的PID。

  • facility参数是用来指定记录消息程序的类型。它让指定的配置文件,将以不同的方式来处理来自不同方式的消息。它的值可能为 LOG_KERN、LOG_USER、LOG_MAIL、LOG_DAEMON、LOG_AUTH、LOG_SYSLOG、LOG_LPR、LOG_NEWS、LOG_UUCP、LOG_CRON 或 LOG_AUTHPRIV。具体每一个值的含义可以查看man手册,本人的英语水平有限,这里就不做详解了。但是对于一般的使用者都会使用默认的 LOG_USER
   facility
       The facility argument is used to specify what type of program is logging the message.  This lets the  configuration  file
       specify that messages from different facilities will be handled differently.

       LOG_AUTH       security/authorization messages

       LOG_AUTHPRIV   security/authorization messages (private)

       LOG_CRON       clock daemon (cron and at)

       LOG_DAEMON     system daemons without separate facility value

       LOG_FTP        ftp daemon

       LOG_KERN       kernel messages (these can't be generated from user processes)

       LOG_LOCAL0 through LOG_LOCAL7
                      reserved for local use

       LOG_LPR        line printer subsystem

       LOG_MAIL       mail subsystem

       LOG_NEWS       USENET news subsystem

       LOG_SYSLOG     messages generated internally by syslogd(8)

       LOG_USER (default)
                      generic user-level messages

       LOG_UUCP       UUCP subsystem

void syslog(int priority, const char *format, ...);   记录至系统记录

  • priority  指的是调试信息的优先级,跟内核中的printk函数类似。内核中定义的各种级别如下:

LOG_EMERG:紧急情况,需要立即通知技术人员。
LOG_ALERT:应该被立即改正的问题,如系统数据库被破坏,ISP连接丢失。
LOG_CRIT:重要情况,如硬盘错误,备用连接丢失。
LOG_ERR:错误,不是非常紧急,在一定时间内修复即可。
LOG_WARNING:警告信息,不是错误,比如系统磁盘使用了85%等。
LOG_NOTICE:不是错误情况,也不需要立即处理。
LOG_INFO:情报信息,正常的系统消息,比如骚扰报告,带宽数据等,不需要处理。
LOG_DEBUG:包含详细的开发情报的信息,通常只在调试一个程序时使用。

void closelog(void);   关闭日志文件,这个函数就没有什么好说的啦,没有任何参数,直接关闭日志文件。

应用实践

#include <stdio.h>
#include <syslog.h>
#include <sys/types.h>
#include <unistd.h>

int main(void)
{
	printf("my pid = %d.\n", getpid());
		
    /*在日志中虽然写了文件名,但是出于准确考虑,也会显示该进程的pid,因为pid才是一个进程的唯一标识*/
	openlog("a.out", LOG_PID | LOG_CONS, LOG_USER);	
		
	syslog(LOG_INFO, "this is my log info.%d", 23);		//使用方法与printk 类似可以格式化的输出
		
	syslog(LOG_INFO, "this is another log info.");
	syslog(LOG_INFO, "this is 3th log info.");
	
	closelog();
}

在Ubuntu中日志在/var/log/syslog文件中,不同linux的发行版路径会不一样,其他的日志可能会在/var/log/messages

syslog的工作原理

(1)操作系统中有一个守护进程syslogd(开机运行,关机时才结束),这个守护进程syslogd负责进行日志文件的写入和维护。

(2)syslogd是独立于我们任意一个进程而运行的。我们当前进程和syslogd进程本来是没有任何关系的,但是我们当前进程可以通过调用openlog打开一个和syslogd相连接的通道,然后通过syslog向syslogd发消息,然后由syslogd来将其写入到日志文件系统中。

(3)syslogd其实就是一个日志文件系统的服务器进程,提供日志服务。任何需要写日志的进程都可以通过openlog/syslog/closelog这三个函数来利用syslogd提供的日志服务。这就是操作系统的服务式的设计。

注明:本博客是根据朱有鹏老师的l《linux嵌入式核心课程》视频所作的总结

猜你喜欢

转载自blog.csdn.net/David_361/article/details/86103667