C++ 中可能出现的线程饥饿问题

问题描述 投票:0回答:1

我有一个

decode
函数,可以解码字符串并在内部使用映射来存储已解码的值以提高效率。该函数由多个线程访问(使用
pthread
),因此为了防止地图并发访问问题,我添加了一个
std::mutex
。然而,在添加互斥体后,我注意到一些线程最终停止工作或似乎被卡住。当我删除互斥锁时,所有线程都运行没有任何问题。

我的问题是:这可能是饥饿的情况吗?我该如何解决这个问题?

其他上下文:此 C++ 代码正在通过 JNI 在 Android 应用程序中使用。

std::unordered_map<std::string, std::pair<int, std::vector<uint8_t>>> decoded_map;
std::mutex decoded_map_mutex;

const char* decode(const char* encodedString) {
    std::string encoded(encodedString);
    std::string decoded;
    
    for (/* some condition */) {
        {
            std::lock_guard<std::mutex> lock(decoded_map_mutex);
            // Operation involving map search
            auto it = decoded_map.find(part);
            if (it != decoded_map.end()) {
                // Some processing
            }
        }
        // Additional processing
        {
            std::lock_guard<std::mutex> lock(decoded_map_mutex);
            decoded_map[part] = std::make_pair(index / 4, bytes);
        }
        
        decode += part;
    }

    return strdup(decoded.c_str());
}
android c++ multithreading mutex
1个回答
0
投票

请勿从具有多个活动线程的程序中调用

fork
。 Android 操作系统基于 Linux 内核,Linux 的
man 2 fork
页面
是这样说的:

   •  The child process is created with a single thread—the one that
      called fork().  The entire virtual address space of the parent
      is replicated in the child, including the states of mutexes,
      condition variables, and other pthreads objects; the use of
      pthread_atfork(3) may be helpful for dealing with problems
      that this can cause.

   •  After a fork() in a multithreaded program, the child can
      safely call only async-signal-safe functions (see
      signal-safety(7)) until such time as it calls execve(2).

除了调用

fork
的线程之外的所有线程都将从子进程中消失。如果其中任何一个互斥体被锁定,那么该互斥体将保持锁定状态,无法解锁。如果其中任何一个有正在进行的工作,那么该工作将是未完成的,(通常)您无法知道已经完成了多少。

您在评论中问:

所以你的意思是如果我有 5 个从主线程启动的线程并且如果我从其中一个线程调用 fork,那么剩下的 4 个线程将被杀死?

fork
调用之后,父进程仍然有五个线程,但子进程只有一个。

© www.soinside.com 2019 - 2024. All rights reserved.