Skip to content

Prctl

provide.foundation.process.prctl

TODO: Add module docstring.

Classes

Functions

get_name

get_name() -> str | None

Get process name (PR_GET_NAME).

Returns:

Type Description
str | None

Process name, or None if prctl is not available

Raises:

Type Description
PlatformError

If not on Linux or python-prctl not installed

Example

from provide.foundation.process import get_name get_name() 'worker-1'

Source code in provide/foundation/process/prctl.py
def get_name() -> str | None:
    """Get process name (PR_GET_NAME).

    Returns:
        Process name, or None if prctl is not available

    Raises:
        PlatformError: If not on Linux or python-prctl not installed

    Example:
        >>> from provide.foundation.process import get_name
        >>> get_name()
        'worker-1'

    """
    _require_prctl()

    try:
        return prctl.get_name()
    except Exception as e:
        log.debug("Failed to get process name", error=str(e))
        return None

has_prctl

has_prctl() -> bool

Check if prctl is available.

Returns:

Type Description
bool

True if running on Linux and python-prctl is installed, False otherwise

Example

from provide.foundation.process import has_prctl if has_prctl(): ... # Use prctl features ... pass

Source code in provide/foundation/process/prctl.py
def has_prctl() -> bool:
    """Check if prctl is available.

    Returns:
        True if running on Linux and python-prctl is installed, False otherwise

    Example:
        >>> from provide.foundation.process import has_prctl
        >>> if has_prctl():
        ...     # Use prctl features
        ...     pass

    """
    return _HAS_PRCTL

is_linux

is_linux() -> bool

Check if running on Linux.

Returns:

Type Description
bool

True if running on Linux, False otherwise

Example

from provide.foundation.process import is_linux is_linux() True

Source code in provide/foundation/process/prctl.py
def is_linux() -> bool:
    """Check if running on Linux.

    Returns:
        True if running on Linux, False otherwise

    Example:
        >>> from provide.foundation.process import is_linux
        >>> is_linux()
        True

    """
    return _IS_LINUX

set_death_signal

set_death_signal(signal: int) -> bool

Set signal to be sent to process when parent dies (PR_SET_PDEATHSIG).

This is useful for ensuring child processes are cleaned up when the parent terminates unexpectedly.

Parameters:

Name Type Description Default
signal int

Signal number to send (e.g., signal.SIGTERM, signal.SIGKILL)

required

Returns:

Type Description
bool

True if successful, False otherwise

Raises:

Type Description
PlatformError

If not on Linux or python-prctl not installed

Example

import signal from provide.foundation.process import set_death_signal set_death_signal(signal.SIGTERM) # Send SIGTERM when parent dies True

Source code in provide/foundation/process/prctl.py
def set_death_signal(signal: int) -> bool:
    """Set signal to be sent to process when parent dies (PR_SET_PDEATHSIG).

    This is useful for ensuring child processes are cleaned up when the parent
    terminates unexpectedly.

    Args:
        signal: Signal number to send (e.g., signal.SIGTERM, signal.SIGKILL)

    Returns:
        True if successful, False otherwise

    Raises:
        PlatformError: If not on Linux or python-prctl not installed

    Example:
        >>> import signal
        >>> from provide.foundation.process import set_death_signal
        >>> set_death_signal(signal.SIGTERM)  # Send SIGTERM when parent dies
        True

    """
    _require_prctl()

    try:
        prctl.set_pdeathsig(signal)
        log.debug("Death signal set", signal=signal)
        return True
    except Exception as e:
        log.warning("Failed to set death signal", signal=signal, error=str(e))
        return False

set_dumpable

set_dumpable(dumpable: bool) -> bool

Set whether process can produce core dumps (PR_SET_DUMPABLE).

Parameters:

Name Type Description Default
dumpable bool

True to allow core dumps, False to disable

required

Returns:

Type Description
bool

True if successful, False otherwise

Raises:

Type Description
PlatformError

If not on Linux or python-prctl not installed

Example

from provide.foundation.process import set_dumpable set_dumpable(False) # Disable core dumps for security True

Source code in provide/foundation/process/prctl.py
def set_dumpable(dumpable: bool) -> bool:
    """Set whether process can produce core dumps (PR_SET_DUMPABLE).

    Args:
        dumpable: True to allow core dumps, False to disable

    Returns:
        True if successful, False otherwise

    Raises:
        PlatformError: If not on Linux or python-prctl not installed

    Example:
        >>> from provide.foundation.process import set_dumpable
        >>> set_dumpable(False)  # Disable core dumps for security
        True

    """
    _require_prctl()

    try:
        prctl.set_dumpable(1 if dumpable else 0)
        log.debug("Dumpable flag set", dumpable=dumpable)
        return True
    except Exception as e:
        log.warning("Failed to set dumpable flag", dumpable=dumpable, error=str(e))
        return False

set_name

set_name(name: str) -> bool

Set process name (PR_SET_NAME).

Note: This is different from setproctitle. PR_SET_NAME sets the comm value in /proc/[pid]/comm (limited to 16 bytes including null terminator).

Parameters:

Name Type Description Default
name str

Process name (max 15 characters)

required

Returns:

Type Description
bool

True if successful, False otherwise

Raises:

Type Description
PlatformError

If not on Linux or python-prctl not installed

Example

from provide.foundation.process import set_name set_name("worker-1") True

Source code in provide/foundation/process/prctl.py
def set_name(name: str) -> bool:
    """Set process name (PR_SET_NAME).

    Note: This is different from setproctitle. PR_SET_NAME sets the comm value
    in /proc/[pid]/comm (limited to 16 bytes including null terminator).

    Args:
        name: Process name (max 15 characters)

    Returns:
        True if successful, False otherwise

    Raises:
        PlatformError: If not on Linux or python-prctl not installed

    Example:
        >>> from provide.foundation.process import set_name
        >>> set_name("worker-1")
        True

    """
    _require_prctl()

    if len(name) > 15:
        log.warning(
            "Process name truncated to 15 characters",
            requested=name,
            actual=name[:15],
        )
        name = name[:15]

    try:
        prctl.set_name(name)
        log.debug("Process name set", name=name)
        return True
    except Exception as e:
        log.warning("Failed to set process name", name=name, error=str(e))
        return False

set_no_new_privs

set_no_new_privs(enabled: bool = True) -> bool

Set no_new_privs flag (PR_SET_NO_NEW_PRIVS).

When enabled, execve() will not grant privileges to do anything that could not have been done without the execve() call. This is a security feature.

Parameters:

Name Type Description Default
enabled bool

True to enable no_new_privs, False to attempt disable (usually fails)

True

Returns:

Type Description
bool

True if successful, False otherwise

Raises:

Type Description
PlatformError

If not on Linux or python-prctl not installed

Example

from provide.foundation.process import set_no_new_privs set_no_new_privs(True) # Prevent privilege escalation True

Source code in provide/foundation/process/prctl.py
def set_no_new_privs(enabled: bool = True) -> bool:
    """Set no_new_privs flag (PR_SET_NO_NEW_PRIVS).

    When enabled, execve() will not grant privileges to do anything that could
    not have been done without the execve() call. This is a security feature.

    Args:
        enabled: True to enable no_new_privs, False to attempt disable (usually fails)

    Returns:
        True if successful, False otherwise

    Raises:
        PlatformError: If not on Linux or python-prctl not installed

    Example:
        >>> from provide.foundation.process import set_no_new_privs
        >>> set_no_new_privs(True)  # Prevent privilege escalation
        True

    """
    _require_prctl()

    try:
        # Note: python-prctl doesn't have direct no_new_privs support
        # This would require direct prctl() syscall
        import ctypes

        # PR_SET_NO_NEW_PRIVS = 38
        # PR_GET_NO_NEW_PRIVS = 39
        libc = ctypes.CDLL(None)
        result = libc.prctl(38, 1 if enabled else 0, 0, 0, 0)
        if result == 0:
            log.debug("no_new_privs flag set", enabled=enabled)
            return True
        log.warning("Failed to set no_new_privs flag", result=result)
        return False
    except Exception as e:
        log.warning("Failed to set no_new_privs flag", enabled=enabled, error=str(e))
        return False