Main Content

CWE Rule 560

Use of umask() with chmod-style Argument

Since R2023a

Description

Rule Description

The product calls umask() with an incorrect argument that is specified as if it is an argument to chmod().

Polyspace Implementation

The rule checker checks for Umask used with chmod-style arguments.

Examples

expand all

Issue

This issue occurs when umask commands have arguments specified in the style of arguments to chmod and provide possibly unintended permissions. For instance:

  • The umask command provides more permissions to the group than the current user.

  • The umask command provides more permissions to other users than the group.

For new files, the umask argument or the mask value specifies which permissions not to set, in other words, which permissions to remove. The mask is bitwise-negated and then applied to new file permissions. In contrast, chmod sets the permissions as you specify them.

Risk

If you use chmod-style arguments, you specify opposite permissions of what you want. This mistake can give external users unintended read/write access to new files and folders.

Fix

To fix this defect, perform both of these tasks:

  • Enable read permission for the user.

  • Set the mask value so that the user (u) has equal or fewer permissions turned off than the group (g) and the group has equal or fewer permissions turned off than other users (o), or u <= g <= o.

You can see the umask value by calling,

umask
or the symbolic value by calling,
umask -S

Example — Setting the Default Mask
#include <stdio.h>
#include <assert.h>
#include <sys/types.h>
#include <sys/stat.h>

typedef mode_t (*umask_func)(mode_t);

const mode_t default_mode = (
    S_IRUSR    /* 00400 */ 
    | S_IWUSR  /* 00200 */ 
    | S_IRGRP  /* 00040 */ 
    | S_IWGRP  /* 00020 */
    | S_IROTH  /* 00004 */
    | S_IWOTH  /* 00002 */
    );         /* 00666 (i.e. -rw-rw-rw-) */

static void my_umask(mode_t mode)
{
    umask(mode);  //Noncompliant
}

int umask_use(mode_t m)
{
    my_umask(default_mode);
    return 0;
}

This example uses a function called my_umask to set the default mask mode. However, the default_mode variable gives the permissions 666 or -rw-rw-rw. umask negates this value. However, this negation means the default mask mode turns off read/write permissions for the user, group users, and other outside users.

Correction — Negate Preferred Permissions

One possible correction is to negate the default_mode argument to my_umask. This correction nullifies the negation umask for new files.

#include <stdio.h>
#include <assert.h>
#include <sys/types.h>
#include <sys/stat.h>

typedef mode_t (*umask_func)(mode_t);

const mode_t default_mode = (
    S_IRUSR    /* 00400 */ 
    | S_IWUSR  /* 00200 */ 
    | S_IRGRP  /* 00040 */ 
    | S_IWGRP  /* 00020 */
    | S_IROTH  /* 00004 */
    | S_IWOTH  /* 00002 */
    );         /* 00666 (i.e. -rw-rw-rw-) */

static void my_umask(mode_t mode)
{
    umask(mode);
}

int umask_use(mode_t m)
{
    my_umask(~default_mode);
    return 0;
}

Check Information

Category: Others

Version History

Introduced in R2023a