您的位置:首页 > 运维架构 > Nginx

nginx之main函数的解读(三)

2014-10-10 21:15 4647 查看
接下来,开始进行函数调用了

ngx_debug_init();
    if (ngx_strerror_init() != NGX_OK) 
	{
        return 1;
    }
ngx_debug_init(),主要是在debug方面,然而,该函数现如今不进行任何操作,可以放过(笔者没有看出比较实质性的操作,大牛路过,可指出错误)

现在说下ngx_strerror_init函数,该函数定义在os文件夹下的unix下的ngx_error.c文件下面

ngx_int_t
ngx_strerror_init(void)
{
    char       *msg;
    u_char     *p;
    size_t      len;
    ngx_err_t   err;
    /*
     * ngx_strerror() is not ready to work at this stage, therefore,
     * malloc() is used and possible errors are logged using strerror().
     */
<pre name="code" class="cpp">    //现在说下NGX_SYS_NERR,该NGX_SYS_NERR只有在安装了nginx之后产生在ngx_auto_config.h
    //#define NGX_SYS_NERR 132其含义就是,在linux系统中有132个错误代码,也就是说,
    //通过使用strerror获得系统中的错误信息,并且填充在ngx_sys_errlist数组中,如果需要使用不再向系统问询
    //而ngx_sys_errlist是定义在ngx_error.c中的全局变量,只是static ngx_str_t  *ngx_sys_errlist;
    len = NGX_SYS_NERR * sizeof(ngx_str_t);
    //使用malloc函数开辟了132个ngx_str_t,当然ngx_str_t内部的空间还没有开辟
    ngx_sys_errlist = malloc(len);
    if (ngx_sys_errlist == NULL) {
        goto failed;
    }
    
    for (err = 0; err < NGX_SYS_NERR; err++) {
        //strerror这样我们就得到了错误编码的错误信息
        msg = strerror(err);
        //len是系统错误信息的字符串长度
        len = ngx_strlen(msg);
        //动态开辟空间,因为是动态的,所以不需要担心被释放
        p = malloc(len);
        if (p == NULL) {
            //开辟失败,进行错误处理
            goto failed;
        }
        //将错误信息放在我们当初开辟的空间当中
        ngx_memcpy(p, msg, len);
        //将错误信息放在ngx_sys_errlist数组当中
        ngx_sys_errlist[err].len = len;
        ngx_sys_errlist[err].data = p;
    }
    return NGX_OK;//原来还可以这么使用标签,在return 后面,学习了
failed:
    err = errno;
    //这样我们将该错误记录到错误日志当中
    ngx_log_stderr(0, "malloc(%uz) failed (%d: %s)", len, err, strerror(err));
    return NGX_ERROR;
}



现在我们说下ngx_log_stderr的函数:

void ngx_cdecl
 ngx_log_stderr(ngx_err_t err, const char *fmt, ...)
 {
     u_char   *p, *last;
     va_list   args;
     u_char    errstr[NGX_MAX_ERROR_STR];//这里面是错误信息的最大长度,该值是定义在core中的ngx_log.g当中其值是2048 
     last = errstr + NGX_MAX_ERROR_STR;//last是错误信息的结束位置
     p = errstr + 7;//p呢,就是错误信息的真正开始 
     ngx_memcpy(errstr, "nginx: ", 7);// 
     va_start(args, fmt);
     p = ngx_vslprintf(p, last, fmt, args);//p应该是在该信息的结束位置
     va_end(args);//这部分呢,就是根据可变参数,将真正的信息放在内存当中p, 
     if (err) {
       //如果错误代码不是0,则系统标准的错误信息放在了p当中,也就是说如果是0,那么就是系统自定义的错误信息,我们需要p中的信息
        p = ngx_log_errno(p, last, err);
     }
     
     if (p > last - NGX_LINEFEED_SIZE) {//NGX_LINEFEED_SIZE放在了os/unix当中的ngx_files.h文件当中该值是1
         //检测p中是否有内容
         p = last - NGX_LINEFEED_SIZE;//如果p和last
     } 
     //
     ngx_linefeed(p); //在p指向后面添加一个"\n"字符,换句话而言就是在nginx:后面加一个换行字符,之后才是真正的信息
<pre name="code" class="cpp">    //ngx_write_console的重定义,就是write(fd,buf,len);而<span class="reserved">#define</span> <a target=_blank class="fid" href="http://lxr.nginx.org/ident?_i=ngx_stderr">ngx_stderr</a>     STDERR_FILENO,直接控制台输出
(void) ngx_write_console(ngx_stderr, errstr, p - errstr); }


这里面的内容有一个函数是ngx_log_errno,该函数记录了真正的错误信息

u_char *
 ngx_log_errno(u_char *buf, u_char *last, ngx_err_t err)
 {
     if (buf > last - 50) {
         //如果错误信息不足50个字符,那么就重新设置50个字符
         /* leave a space for an error code */ 
         buf = last - 50;
         *buf++ = '.';
         *buf++ = '.';
         *buf++ = '.';
     } 
 #if (NGX_WIN32)
     buf = ngx_slprintf(buf, last, ((unsigned) err < 0x80000000)
                                        ? " (%d: " : " (%Xd: ", err);//这样,在win32系统下,转换成相应的错误代码,这也是一个可变参数转换成字符串
 #else
     buf = ngx_slprintf(buf, last, " (%d: ", err);//同上
 #endif 
     buf = ngx_strerror(err, buf, last - buf); //这部分函数检错错误信息是否是已知的,从而将错误信息放在buf当中,不是,也放在了buf当中
     if (buf < last) {
         *buf++ = ')';
     } 
     return buf;
 }


而ngx_strerror函数应该是

u_char *
 ngx_strerror(ngx_err_t err, u_char *errstr, size_t size)
 {
     ngx_str_t  *msg;
 
     msg = ((ngx_uint_t) err < NGX_SYS_NERR) ? &ngx_sys_errlist[err]://这样,我们就可以知道,错误代码是否小于132,进而判断错误信息是否在ngx_sys_errlist中
                                               &ngx_unknown_error;
     size = ngx_min(size, msg->len);
 
     return ngx_cpymem(errstr, msg->data, size);//最后将原来存储的错误信息放在errstr当中
 }
那么日志记录部分就结束了
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: