- 云原生安全:攻防实践与体系构建
- 刘文懋 江国龙 浦明 阮博男 叶晓虎
- 550字
- 2021-11-04 18:12:36
4.3.4 漏洞修复
官方针对此漏洞的补丁[1]很容易理解,即在API Server中增加了对后端服务器(如Kubelet)返回值的判断:
//determine the http response code from the backend by reading from rawResponse+backendConn rawResponseCode, headerBytes, err := getResponseCode(io.MultiReader(bytes. NewReader(rawResponse), backendConn)) //... if rawResponseCode != http.StatusSwitchingProtocols { //If the backend did not upgrade the request, finish echoing the response from the backend to the client and return, closing the connection. glog.V(6).Infof("Proxy upgrade error, status code %d", rawResponseCode) _, err := io.Copy(requestHijackedConn, backendConn) if err != nil && !strings.Contains(err.Error(), "use of closed network connection") { glog.Errorf("Error proxying data from backend to client: %v", err) } //Indicate we handled the request return true } //... //getResponseCode reads a http response from the given reader, returns the status code, //the bytes read from the reader, and any error encountered func getResponseCode(r io.Reader) (int, []byte, error) { rawResponse := bytes.NewBuffer(make([]byte, 0, 256)) //Save the bytes read while reading the response headers into the rawResponse buffer resp, err := http.ReadResponse(bufio.NewReader(io.TeeReader(r, rawResponse)), nil) if err != nil { return 0, nil, err } //return the http status code and the raw bytes consumed from the reader in the process return resp.StatusCode, rawResponse.Bytes(), nil }
增加的逻辑会判断后端返回码是否等于http.StatusSwitchingProtocols(即101状态码)。如果不等,则直接返回,关闭连接;只有在相等的情况下,代理通道才会建立。
这样一来,第一步中攻击者以出错方式调用/api/v1/namespaces/{namespace}/pods/{pod}/exec来建立到Kubelet的通道的尝试就会失败,后续攻击自然无法展开。
CVE-2018-1002105是云原生环境下少见的高危漏洞之一,CVSS 3.x评分达到了9.8,而2019年流传甚广的runC漏洞CVE-2019-5736的CVSS 3.x评分也不过8.6,其严重性可见一斑。这样一个漏洞,轻则泄露数据,重则允许攻击者接管集群。
更加值得注意的是,漏洞的触发过程完全在RESTful API层面进行,其行为特征并不明显,日志排查难度也很高。因此,除了及时更新补丁外,如何有效检测这一类隐蔽性高的云原生安全漏洞的利用行为,或进一步而言,如何针对云原生环境建立有效的API异常检测系统,是需要云安全从业者认真考虑的问题。
[1] https://github.com/kubernetes/kubernetes/pull/71412/commits/b84e3dd6f80af4016acfd891ef6cc50ce05d4b5b。