c - 互斥锁是否仅在所有相关线程尝试在利用资源之前尝试获取其应获取的锁的情况下才能正常工作?

标签 c multithreading kernel mutex

在第一次上OS课之前,我只是第一次学习锁。我最初认为锁实际上是“锁定某些资源”,您需要在其中指定资源(也许通过指向内存中资源的地址的指针),但是在阅读了几个自旋锁的真正基本实现之后(例如,类Unix的培训操作系统“xv6”的版本):
http://pages.cs.wisc.edu/~skobov/cs537/P3/xv6/kernel/spinlock.h
http://pages.cs.wisc.edu/~skobov/cs537/P3/xv6/kernel/spinlock.c
以及之前的堆栈溢出问题:(What part of memory does a mutex lock? (pthreads))
我想我都错了。
相反,在我看来,锁实际上只是一个 bool 型标志,如变量,它临时(或无限期)地阻止某些将利用资源的代码的执行,但仅在另一个线程实际上也尝试获取该锁的位置(在第二个线程中的那个位置)尝试也获取该锁,则第二线程的阻塞具有该副作用,即该第二线程在第一线程释放该锁之前不能利用资源。因此,现在我想知道的是:如果一个设计不良的线程不使用互斥锁,而只是试图利用另一个设计良好的线程所锁定的资源,那么设计不良的线程是否能够访问该资源(无论如何,只要忽略该变量即可)。互斥锁-我现在正在考虑充当线程应查看的标志,但是有机会忽略它)?
如果是这样,那么为什么我们将锁实现为复杂的 bool 变量,以使所有线程都必须使用锁,而不是阻止访问内存区域的锁?
由于我对这一切还比较陌生,因此,如果我错误地陈述了我的问题以及答案,我将感谢任何合理的术语编辑建议!
非常感谢你!
--edit,谢谢大家的及时和有益的回复!

最佳答案

If that's the case, then why do we implement locks as sophisticated boolean variables such that all threads must use the locks as opposed to a lock that instead prevents access to a memory region?


原因很多:
  • 如果您要控制的对象不是存储区怎么办?如果是文件或网络连接怎么办?
  • 编译器将如何知道何时要访问 protected 内存区域?编译器是否必须假设任何地方的任何内存访问都可以与其他线程同步?这将使许多优化变得不可能,包括可能将共享变量存储在寄存器中,这一点非常关键。
  • 硬件是否必须支持任何粒度的锁定内存?它如何知道与对象关联的内存?考虑一个链表。您是否必须锁定与该链接列表关联的所有内存及其中的每个对象?在列表中添加或删除对象时,是否需要更改 protected 内存?那既昂贵又很难使用吗?
  • 它怎么知道何时释放锁?假设您访问需要保护的内存区域,然后再访问其他内存区域。实现如何知道是否可以允许其他线程在这两次访问之间访问该区域?实现将需要知道访问该区域的代码是否依赖于这两次访问上共享状态的一致 View 。它怎么知道呢?保持锁定会出错,并发会受到影响。通过释放两次访问之间的锁定来弄错它,并且代码可能无法正常运行。

  • 等等。

    关于c - 互斥锁是否仅在所有相关线程尝试在利用资源之前尝试获取其应获取的锁的情况下才能正常工作?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62642917/

    相关文章:

    c - 线程不并行运行

    c - 不同的静态全局变量共享相同的内存地址

    c - C 如何将 double 存储到已分配的 float 类型数组中?

    multithreading - linux如何管理线程栈

    linux - pt_regs 结构中的 eax 在哪里?只有斧头存在

    linux - 在进程退出之前从/proc中提取进程的所有统计信息(Linux)

    c# - 在 Windows 上将数据插入文件

    c++ - 多线程:thread 或 process.h - C++

    c++ - 如何将带参数的愚蠢函数添加到愚蠢的执行程序中?

    linux - Linux 信号在内核内部的什么地方发送或处理?