slock

Java: Java终止线程的几种方式

安稳与你 提交于 2021-02-12 04:23:38
首先说明,使用stop方法终止的方式已经在很久之前就被废弃了,在加锁的情况下有可能会造成死锁,这里不做讨论。 1. 使用标志位终止线程 在run()方法执行完毕后,该线程就终止了。但是在某些特殊的情况下,希望run()方法中的代码一直循环执行。比如在服务端程序中可能会使用 while(true) { ... } 这样的循环结构来不断的接收来自客户端的请求。此时就可以用修改标志位的方式来结束 run() 方法。例: public class ServerThread extends Thread { // volatile修饰符用来保证其它线程读取的总是该变量的最新的值 public volatile boolean exit = false ; @Override public void run() { ServerSocket serverSocket = new ServerSocket(8080 ); while (! exit){ serverSocket.accept(); // 阻塞等待客户端消息 ... } } public static void main(String[] args) { ServerThread t = new ServerThread(); t.start(); ... t.exit = true ; // 修改标志位,退出线程 } }

Linux内核中锁机制之原子操作、自旋锁

。_饼干妹妹 提交于 2020-12-14 04:42:50
很多人会问这样的问题,Linux内核中提供了各式各样的同步锁机制到底有何作用?追根到底其实是由于操作系统中存在多进程对共享资源的并发访问,从而引起了进程间的竞态。这其中包括了我们所熟知的SMP系统,多核间的相互竞争资源,单CPU之间的相互竞争,中断和进程间的相互抢占等诸多问题。 通常情况下,如图 1所示,对于一段程序,我们的理想是总是美好的,希望它能够这样执行:进程 1先对临界区完成操作,然后进程 2再去操作临界区。但是往往现实总是残酷的,进程 1在执行过程中,进程 2很可能在此插入一脚,导致两个进程同时对临界区进行读写访问,读是没有问题,但写的话问题就大了。这样的话,得到的结果往往不是我们想要的。 图 1 一个简单的例子 因此,我们需要一些解决方法,在 Linux内核中它提供了如下几种锁机制,供用户在针对不同情况分别或配合使用,包括:原子操作、自旋锁、内存屏障、读写自旋锁、顺序锁、信号量、读写信号量、完成量、 RCU机制、 BKL(大内核锁 )等等,下面笔者将分五篇博文一一讨论这些锁机制。另外,本文所涉及的关于 Linux内核源码采用版本为: Linux 3.3.1。 OK,让我们首先讨论有关原子操作和自旋锁的相关内容吧。 一、原子操作 所谓的原子操作即是保证指令以原子的方式执行,它在执行过程中不被打断。它包括了原子整数操作和原子位操作,在内核中分别定义于 include

Linux并发与同步专题 (2)spinlock

不羁的心 提交于 2020-12-03 11:53:51
关键词: wfe、FIFO ticket-based、spin_lock/spin_trylock/spin_unlock、spin_lock_irq/spin_lock_bh/spin_lock_irqsave 。 《 Linux并发与同步专题 (1)原子操作和内存屏障 》 《 Linux并发与同步专题 (2)spinlock 》 《 Linux并发与同步专题 (3) 信号量 》 《 Linux并发与同步专题 (4) Mutex互斥量 》 《 Linux并发与同步专题 (5) 读写锁 》 《 Linux并发与同步专题 (6) RCU 》 《 Linux并发与同步专题 (7) 内存管理中的锁 》 《 Linux并发与同步专题 (8) 最新更新与展望 》 spinlock同一时刻只能被一个内核代码路径持有,如果有另外一个内核代码路径试图获取一个已经被持有的spinlock,那么该内核代码路径需要一直自旋忙等待,直到锁持有者释放了该锁。 spinlock锁的特性如下: spinlock属于忙等待机制,当无法获取spinlock锁时会不断尝试,直到获取锁为止。 同一时刻只能有一个内核代码路径可以获得所。 要求spinlock锁持有者尽快完成临界区的执行任务。如果临界区执行时间过长,在锁外面忙等待的CPU比较浪费,特别是spinlock临界区里不能睡眠。