Linux中断基础概念

基于内核3.8

对于Linux中断,硬件中断(中断的上半部分)没有什么基础概念,主要源自中断的下半部(BH)。

在讲解中断之前,首先讲解线程结构体,这里主要关注struct thread_info 结构体,其结构如下:

1. 变量:preempt_count

我们在提到,一个线程的禁止被抢占的时候,可能比较好理解,因为线程结构体里面有这个preempt_count成员,如果禁止被抢占,即增加这个技术就可以了。可是当我们提到在中断中禁止中断被抢占(一般指中断下半部-软中断,上半部主要是针对中断嵌套),里面用到的依然是这个变量,那么在软中断(或中断)中使用的是不是这个变量呢?答案是是肯定的。因为不管我们是硬中断抢占软中断,还是硬中断抢占线程,还是软中断抢占线程,其实归根结底都是抢占的线程。

struct thread_info {
	struct task_struct *task;		/* main task structure */
	struct exec_domain *exec_domain;	/* execution domain */
	int		cpu;			/* cpu we're on */
	int		preempt_count;		/* 0 => preemptable,
						   <0 => BUG */
	int		preempt_lazy_count;	/* 0 => preemptable,
						   <0 => BUG */
	struct restart_block restart_block;
	unsigned long	local_flags;		/* private flags for thread */

	/* low level flags - has atomic operations done on it */
	unsigned long	flags ____cacheline_aligned_in_smp;
};

线程变量preempt_count,主要分4个部分,如下所示:

bit31-24(区域A)bit23-16(区域B)bit15-8(区域C)bit7-0(区域D)
其他 硬中断计数软中断计数普通抢占

如果线程禁止其他线程抢占,通过调用宏:preempt_disable(),其做的工作主要是增加线程的preempt_count的值,其实也就是增加了这个值的区域D的值,如果其要禁止中断下半部抢占的话就在下半部对于的区域C增加一个值。依次类推。

2. 关于软中断:

在《Linux内核设计与实现》一书中提到同一个CPU上面只允许软中断的一个实例运行,当时我一直没有弄明白这句话是什么意思。正如我们所知的,关于软中断每个CPU都维持着一个32位的位图,这个位图中的每一位都对应着一个类型的软中断,为什么要一个类型而不是一个软中断呢?主要由于里面的软中断有的是tasklet,如下内核的定义:

enum
{
	HI_SOFTIRQ=0,
	TIMER_SOFTIRQ,
	NET_TX_SOFTIRQ,
	NET_RX_SOFTIRQ,
	BLOCK_SOFTIRQ,
	BLOCK_IOPOLL_SOFTIRQ,
	TASKLET_SOFTIRQ,
	SCHED_SOFTIRQ,
	HRTIMER_SOFTIRQ,
	RCU_SOFTIRQ,    /* Preferable RCU should always be the last softirq */

	NR_SOFTIRQS
};

这个是我们在linux-3.8中定义的软中断,上面的HI_SOFTIRQ和TASKLET_SOFTIRQ我们看到的是tasklet的下半部,这个可能对应很多下半部。所以说每个CPU维持的这个位图每一位对应着是一类软中断。对于同一个CPU只能运行一个软中断实例以及同一个软中断实例可以在不同的CPU上运行这部分的讲解将在后续描述!


 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值