rt-thread icon indicating copy to clipboard operation
rt-thread copied to clipboard

[Bug] Insufficient parameter validation vulnerability in the sys_sigprocmask system call in Smart version of RT-Thread

Open x-codingman opened this issue 7 months ago • 0 comments

RT-Thread Version

v5.1.0

Hardware Type/Architectures

Not apply

Develop Toolchain

Other

Describe the bug

Summary

I have identified a vulnerability in the sys_sigprocmask system call in the Smart version of RT-Thread v5.1.0. This vulnerability stems from insufficient validation of the how parameter, which is used as an array index without proper bounds checking. If exploited by a compromised user thread, this issue could lead to severe security consequences, including kernel crashes and potential unauthorized memory access.

Vulnerable Code Location

The vulnerability is present in the rt-thread/components/lwp/lwp_syscall.c file. The issue arises from the lack of proper validation of the how parameter pointer. The code location of this vulnerability is as follows:

rt-thread/components/lwp/lwp_syscall.csysret_t sys_sigprocmask(int how, const sigset_t *sigset, sigset_t *oset, size_t size)

sysret_t sys_sigprocmask(int how, const sigset_t *sigset, sigset_t *oset, size_t size)
{
    int ret = -1;
    lwp_sigset_t *pnewset = RT_NULL, *poldset = RT_NULL;
#ifdef ARCH_MM_MMU
    lwp_sigset_t newset, oldset;
#endif /* ARCH_MM_MMU*/

    if (!size)
    {
        return -EINVAL;
    }
    if (!oset && !sigset)
    {
        return -EINVAL;
    }
    if (size > sizeof(lwp_sigset_t))
    {
        size = sizeof(lwp_sigset_t);
    }
    if (oset)
    {
#ifdef ARCH_MM_MMU
        if (!lwp_user_accessable((void *)oset, size))
        {
            return -EFAULT;
        }
        poldset = &oldset;
#else
        if (!lwp_user_accessable((void *)oset, size))
        {
            return -EFAULT;
        }
        poldset = (lwp_sigset_t *)oset;
#endif
    }
    if (sigset)
    {
#ifdef ARCH_MM_MMU
        if (!lwp_user_accessable((void *)sigset, size))
        {
            return -EFAULT;
        }
        lwp_get_from_user(&newset, (void *)sigset, size);
        pnewset = &newset;
#else
        if (!lwp_user_accessable((void *)sigset, size))
        {
            return -EFAULT;
        }
        pnewset = (lwp_sigset_t *)sigset;
#endif /* ARCH_MM_MMU */
    }
    ret = lwp_thread_signal_mask(rt_thread_self(), mask_command_u2k[how], pnewset, poldset); // Vulnerability: how parameter is not validated before being used as an array index.
#ifdef ARCH_MM_MMU
    if (ret < 0)
    {
        return ret;
    }
    if (oset)
    {
        lwp_put_to_user(oset, poldset, size);
    }
#endif /* ARCH_MM_MMU */
    return (ret < 0 ? -EFAULT: ret);
}

Vulnerability Description

The vulnerability exists in the sys_sigprocmask function's handling of the how parameter. The code uses how as an index into the mask_command_u2k array without validating its bounds. This oversight can lead to an out-of-bounds array access. The issue is particularly critical because:

  1. The how parameter is passed directly from user space to kernel space
  2. No validation is performed to ensure how is within the valid range of mask_command_u2k array
  3. The value is used directly as an array index: mask_command_u2k[how]
  4. This could lead to accessing memory outside the array bounds

Impact

This vulnerability has severe security implications:

  1. Kernel Crash: The most immediate impact is a potential kernel crash due to out-of-bounds memory access, leading to a Denial of Service (DoS) condition.
  2. Privilege Escalation: In certain scenarios, this vulnerability could potentially be exploited to access kernel memory, leading to privilege escalation.

Other additional context

No response

x-codingman avatar May 20 '25 05:05 x-codingman