Linux部署jar包,隐藏命令行参数

  • 一、背景需求
  • 二、查阅资料
  • 三、实现隐藏库
  • 3.1、测试test.c
  • 3.2、设置隐藏库
  • 3.3、验证
  • 四、应用jar启动命令
  • 五、直接应用结果


所有都配置好了,发现一个致命问题,使用 ps -ef | grep java 可以清晰的看到秘钥,裂开了啊!

一、背景需求

1、不能改动任何的代码。
2、隐藏 nohup 启动命令里面的配置参数。

二、查阅资料

大部分都是按照C的思路处理,将配置参数提前写入内存中,然后在启动的时候,通过指针指向对应的配置,以达到隐藏配置的目的。
依据这个链接,学习了一下:https://zhuanlan.zhihu.com/p/610215116?utm_id=0

三、实现隐藏库

新建一个目录

cd /
mkdir test
cd test

3.1、测试test.c

新增测试文件

touch test.c

测试程序: test.c

#include <stdio.h>

int main(int argc,char **argv){
	printf("argc=%d\n",argc);
	printf("argv[0]=%s\n",argv[0]);
	printf("argv[1]=%s\n",argv[1]);
	printf("argv[2]=%s\n",argv[2]);
	getchar();
	return 0;
}

编译测试程序

gcc test.c

运行测试程序

./a.out 123 456

java 修改启动输出展示 java启动命令_jar

查看进程

ps -ef

java 修改启动输出展示 java启动命令_jar_02

进程的查看结果,直接运行命令行参数用ps命令直接打印了出来。
现在要做的就是把后面的参数隐藏起来。

3.2、设置隐藏库

隐藏库程序 hide.c

touch hide.c

编写代码 hide.c

#define _GNU_SOURCE
#include <dlfcn.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int (*main_bak) (int, char **, char **);
/*
 * 所有的argv指向的内存先备份,然后全部改为*,再将argv指针指向备份内存
 */
static int mymain(int argc, char **argv, char **env) {
	int ret = 0,i = 0,len = 0;
	char **argvbak = NULL;
	if(argc > 1){
		argvbak=(char **)calloc(argc,sizeof(char *));
		for(i = 1;i < argc;i++){
			len = strlen(argv[i]);
			argvbak[i] = (char *)calloc(len,sizeof(char));
			strcpy(argvbak[i],argv[i]);
			strncpy(argv[i],"*",strlen(argv[i]));
			argv[i] = argvbak[i];
		}
	}
	ret = main_bak(argc, argv, env);
	if(argc > 1){
		for(i = 1;i < argc;i++){
			free(argvbak[i]);
		}
		free(argvbak);
	}
	return ret;
}
int (*__next_libc_start_main)(int (*main)(int, char **, char **),
	    int argc,
	    char **argv,
	    void (*init) (void),
	    void (*fini) (void),
	    void (*_fini) (void),
	    void (*stack_end));
int __libc_start_main(int (*main)(int, char **, char **),
		     int argc, char **argv,
		     void (*init)(void),
		     void (*fini)(void),
		     void (*_fini)(void),
		     void (*stack_end))
{
	__next_libc_start_main = dlsym(RTLD_NEXT, "__libc_start_main");
	main_bak = main;
	return __next_libc_start_main(mymain, argc, argv, init, fini, _fini, stack_end);
}

编译代码 hide.c

gcc -O2 -fPIC -shared -o hide.so hide.c -ldl

java 修改启动输出展示 java启动命令_java 修改启动输出展示_03

3.3、验证

使用参数隐藏的方式运行程序

LD_PRELOAD=./hide.so ./a.out 111 222

java 修改启动输出展示 java启动命令_运维_04


查看进程

java 修改启动输出展示 java启动命令_java 修改启动输出展示_05


以上便实现了 隐藏

四、应用jar启动命令

原项目的启动命令:

nohup java -jar -Djasypt.encryptor.password='1234qwer' /app/web.jar --server.port=8080 --spring.config.location=/app/web.yml >> /app/web.out 2>&1 &

在此基础上采用隐藏库即可,及命令前加上 LD_PRELOAD,如下:

LD_PRELOAD=./hide.so nohup java -jar -Djasypt.encryptor.password='1234qwer' /app/web.jar --server.port=8080 --spring.config.location=/app/web.yml >> /app/web.out 2>&1 &

如果再其他地方启动,使用绝对路径即可:

LD_PRELOAD=/test/hide.so nohup java -jar -Djasypt.encryptor.password='1234qwer' /app/web.jar --server.port=8080 --spring.config.location=/app/web.yml >> /app/web.out 2>&1 &

执行完成之后,查看项目进程

ps -ef |grep java

java 修改启动输出展示 java启动命令_linux_06

五、直接应用结果

1、直接下载.so文件
百度网盘地址:https://pan.baidu.com/s/1HcPlHjRpBsmUTU8GnAhKfg?pwd=dge1 提取码:dge1

2、放到服务器里,在启动命令前添加下面命令即可。

LD_PRELOAD=/my/hide.so

地址需根据放服务器的位置调整。

参考链接:
Java 程序隐藏命令行参数:https://www.5axxw.com/wenku/pg/5100338h.html
如何隐藏进程的启动参数?:https://www.zhihu.com/question/27518530
linux小妙招-隐藏命令行参数(不修改源码):https://zhuanlan.zhihu.com/p/610215116?utm_id=0