CWE-364: Signal Handler Race Condition(信号处理程序竞争条件)

 ID: 364

类型:基础
结构:简单

状态:未完成

描述

软件使用引入竞争条件的信号处理程序。

扩展描述

竞争条件经常发生在信号处理程序中,因为信号处理程序支持异步操作。这些竞争状况有多种根本原因和表现。攻击者可能能够利用信号处理程序争用条件导致软件状态损坏,可能导致拒绝服务甚至代码执行。

当不可重入函数或状态敏感操作在信号处理程序中发生时,就会出现这些问题,在信号处理程序中可以随时调用它们。这些行为可能违反被中断的“常规”代码或其他可能被调用的信号处理程序所做的假设。如果在不适当的时刻调用这些函数(例如,当一个不可重入函数已经在运行时),可能会发生内存损坏,这可能会被利用来执行代码。当在信号处理程序中调用free时,通常会出现另一个信号争用条件,这会导致双重空闲,因此会产生一个任意写入的情形。即使给定指针在释放后设置为空,在释放内存和将指针设置为空之间仍存在争用条件。如果为多个信号设置了相同的信号处理程序,这就特别有问题,因为这意味着信号处理程序本身可以重新输入。

有几个已知的与接收到“信号处理程序竞争条件”标签的信号处理程序相关的行为:

•信号处理程序和“常规”代码都可以访问的共享状态(例如全局数据或静态变量)

  • 信号处理程序和其他信号处理程序之间的共享状态
  • 在信号处理程序中使用不可重入功能——这通常意味着正在使用共享状态。例如,malloc()和free()是不可重入的,因为它们可能使用全局或静态数据结构来管理内存,并且它们被无辜的表面函数(如syslog())间接使用;这些函数可能会因内存损坏和代码执行而被利用。
  • 同一信号处理函数与多个信号的关联-这可能意味着共享状态,因为访问相同的代码和资源。例如,这可能是双重免费的来源,并在免费后使用弱点。
  • 使用setjmp和longjmp,或其他阻止信号处理程序将控制返回到原始功能的机制
  • 虽然在技术上不是争用条件,但某些信号处理程序设计为最多调用一次,并且多次调用可能会导致安全问题,即使没有对信号处理程序的任何并发调用。这可能是一个来源,双重释放和释放后使用的弱点。
  • 信号处理程序漏洞通常是基于缺少特定保护机制而进行分类的,尽管在CWE中不鼓励这种类型的分类,因为程序员通常可以选择几种不同的机制来解决弱点。这种保护机制可能保留对共享资源的访问的排他性,以及相关代码的行为原子性:

•避免共享状态

•在信号处理器中使用同步

•在常规代码中使用同步

•禁用或屏蔽其他信号,提供原子性(有效地确保排他性)

相关视图

与“研究层面”视图(CWE-1000)相关

与“开发层面”视图(CWE-699)相关

引入模式

阶段

说明

架构与设计

 

实现

 

应用平台

语言

C (有时出现)

C++ (有时出现))

后果

范围

冲击

可能性

完整性
保密性
可利用性

技术冲击: 修改应用数据 修改内存; DoS: 崩溃、推出或者重启: 执行未获授权的代码或命令

可能会导致数据损坏,并可能通过在意外的时间修改全局变量或数据结构来执行任意代码,这违反了使用此全局数据的代码的假设。

 

访问控制

技术冲击: 获得特权或获得身份

如果信号处理程序中断了以特权执行的代码,那么信号处理程序也可能以提升的特权执行,这可能会使后续的攻击更加严重。

 

被利用的可能性:

一般

示例

例1

此代码用两个不同的信号(CWE-831)注册相同的信号处理程序功能。如果这些信号被发送到进程,处理程序将创建一条日志消息(在程序的第一个参数中指定)并退出。(问题代码)

Example Language:

char *logMessage;

void handler (int sigNum) {

syslog(LOG_NOTICE, "%s\n", logMessage);
free(logMessage);
/* artificially increase the size of the timing window to make demonstration of this weakness easier. */

sleep(10);
exit(0);

}

int main (int argc, char* argv[]) {

logMessage = strdup(argv[1]);
/* Register signal handlers. */

signal(SIGHUP, handler);
signal(SIGTERM, handler);
/* artificially increase the size of the timing window to make demonstration of this weakness easier. */

sleep(10);

}

handler函数使用全局状态(globalvar和logmessage),它可以由sightup和sigterm信号调用。攻击场景可能遵循以下几行:

•程序开始执行,初始化logmessage,并注册信号处理程序以进行叹息和sigterm。

•程序开始其“正常”功能,简化为sleep(),但可能是任何需要一段时间的功能。

•攻击者发送sighup,调用handler(称为“sighup handler”)。

•Sightup处理程序开始执行,调用Syslog()。

•syslog()调用malloc(),这是不可重入的。malloc()开始修改元数据以管理堆。

•然后攻击者发送sigterm。

•叹息处理程序被中断,但Syslog的malloc调用仍在执行,尚未完成对元数据的修改。

•调用sigterm处理程序。

•sigterm handler使用syslog()记录日志消息,然后释放log message变量。

此时,堆的状态不确定,因为malloc仍在修改堆的元数据;元数据可能处于不一致的状态。对free()的sigterm处理程序调用假定元数据不一致,可能导致它在管理堆时将数据写入错误的位置。结果导致内存损坏,这可能导致崩溃,甚至代码执行,具体取决于代码运行的环境。

请注意,这是对Michal Zalewski[Ref-360]最初提出的经典示例的改编;原始示例显示可用于代码执行。

还要注意,这是对Michal Zalewski[Ref-360]最初提出的经典示例的改编;原始示例显示可用于代码执行。

例2

下面的代码用多个信号注册一个信号处理程序,以便在特定事件发生时进行日志记录,并在退出前释放关联的内存。

(问题代码)

Example Language:

#include <signal.h>
#include <syslog.h>
#include <string.h>
#include <stdlib.h>

void *global1, *global2;
char *what;
void sh (int dummy) {

syslog(LOG_NOTICE,"%s\n",what);
free(global2);
free(global1);
/* Sleep statements added to expand timing window for race condition */

sleep(10);
exit(0);

}

int main (int argc,char* argv[]) {

what=argv[1];
global1=strdup(argv[2]);
global2=malloc(340);
signal(SIGHUP,sh);
signal(SIGTERM,sh);
/* Sleep statements added to expand timing window for race condition */

sleep(10);
exit(0);

}

  1. 但是,以下事件序列可能导致双重自由(CWE-415):
  2. 向流程发送叹息
  3. .调用sh()来处理叹息
  4. .第一次调用sh()到达释放global1的点
  5. .此时,向进程发送一个sigterm
  6. 第二次调用sh()可能会再次释放global1
  7. 这导致双自由(CWE-415)

这只是对上述代码的一种可能的利用。另一个例子是,syslog调用可能使用不异步信号安全的malloc调用。这可能导致堆管理结构的损坏。有关更多详细信息,请参阅“为乐趣和利润传递信号”中的示例[Ref-360]。

应对措施

阶段: 需求

策略: 语言选择

使用不允许出现这种弱点的语言,或提供使这种弱点更容易避免的结构。

阶段: 架构与设计

将信号处理程序设计为只设置标志,而不是执行复杂的功能。然后可以在主程序循环中检查和操作这些标志。

阶段: 实现

只在信号处理程序中使用可重入函数。此外,在执行影响执行状态的异步操作时,使用健全性检查确保状态一致。

种属

关系

类型

ID

名称

属于

361

7PK - Time and State

属于

884

CWE Cross-section

属于

986

SFP Secondary Cluster: Missing Lock

说明

研究空白

可能仍然在研究。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值