Nginx隐藏版本号

安装Nginx以后,在服务启动时会显示Nginx的版本号等信息,但是有时候我们并不希望对方可以直接获取相关的版本信息,毕竟暴露版本,找起漏洞就更方便了,那么如何处理这个问题呢?

默认情况

默认情况下,可以轻易的获取nginx版本,比如使用curl命令:

1
2
3
4
5
6
7
8
9
10
$ curl -i localhost:8080
HTTP/1.1 200 OK
Server: nginx/1.16.1
Date: Tue, 31 Mar 2020 16:15:09 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 31 Mar 2020 16:11:47 GMT
Connection: keep-alive
ETag: "5e836bc3-264"
Accept-Ranges: bytes

如何隐藏版本号

最简单的做法,根据官方文档的描述:

Syntax: server_tokens on | off | build | string;
Default: server_tokens on;
Context: http, server, location

Enables or disables emitting nginx version on error pages and in the “Server” response header field.

nginx.conf中的http {}块内加入server_tokens off;,可以将服务版本号进行隐藏,再通过curl、wappalyzer去测试,已经看不到具体版本号了。

1
2
3
4
5
6
7
8
9
10
$ curl -i localhost:8080
HTTP/1.1 200 OK
Server: nginx
Date: Tue, 31 Mar 2020 16:18:14 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 31 Mar 2020 16:11:47 GMT
Connection: keep-alive
ETag: "5e836bc3-264"
Accept-Ranges: bytes

用nmap进行简单的探测,也没有显示具体的版本:

1
2
3
4
PORT     STATE SERVICE VERSION
22/tcp open ssh OpenSSH 7.6p1 Ubuntu 4ubuntu0.3 (Ubuntu Linux; protocol 2.0)
80/tcp open http Apache httpd 2.4.29
8080/tcp open http nginx

更深一层

如果不想让对方知道自己在用Nginx的话,那么需要对一部分源码进行修改,打开Nginx源码的目录:

1、在src/core/nginx.h文件内可以看到下面几个宏定义,对NGINX_VERSIONNGINX_VER进行任意的修改,比如空字符串或者Tengine等😃

1
2
3
#define nginx_version      1016001
#define NGINX_VERSION "1.16.1"
#define NGINX_VER "nginx/" NGINX_VERSION

2、打开src/http/ngx_http_header_filter_module.c文件可以看到下面这一行,我们将nginx删掉:

1
static u_char ngx_http_server_string[] = "Server: nginx" CRLF;

3、打开src/http/ngx_http_special_response.c文件,其实这个文件里面可以修改很多东西,我们先改最明显的,将ngx_http_error_tail中的nginx删掉:

1
2
3
4
5
static u_char ngx_http_error_tail[] =
"<hr><center>nginx</center>" CRLF
"</body>" CRLF
"</html>" CRLF
;

这里还可以将其他错误码信息进行修改,比如404,把404 Not Found改为404:

1
2
3
4
5
6
static char ngx_http_error_404_page[] =
"<html>" CRLF
"<head><title>404 Not Found</title></head>" CRLF
"<body>" CRLF
"<center><h1>404 Not Found</h1></center>" CRLF
;

这样修改完,就基本隐藏的差不多了,重新进行编译和更新,再次通过curl、wappalyzer进行验证,都无法看到Nginx字样:

1
2
3
4
5
6
7
8
9
10
$ curl -i localhost:8080
HTTP/1.1 200 OK
Server:
Date: Tue, 31 Mar 2020 16:53:35 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 31 Mar 2020 16:11:47 GMT
Connection: keep-alive
ETag: "5e836bc3-264"
Accept-Ranges: bytes

再次用nmap进行探测:

1
2
3
4
PORT     STATE SERVICE    VERSION
22/tcp open ssh OpenSSH 7.6p1 Ubuntu 4ubuntu0.3 (Ubuntu Linux; protocol 2.0)
80/tcp open http Apache httpd 2.4.29
8080/tcp open http-proxy

可以看到8080端口的服务已经从之前的nginx变成了http-proxy,当然如果上面改成了Tengine,扫描结果也是Tengine,还是有一点点用的,起码能起到一些混淆作用😂

0%