본문 바로가기

Linux(Centos or RHEL)/RHEL 기초

인터럽트 디스크립터...?

아래의 블로그를 참고하여 글을 작성하였습니다. 제가 공부할 때 참조한 커널 버전은 v2.6.39.4입니다.

http://rousalome.egloos.com/10012152

 

인터럽트 핸들러

인터럽트 벡터

인터럽트 디스크립터

인터럽트 컨텍스트

 

앞에서 인터럽트 벡터에 대해서 공부해 보았으니, 이제 인터럽트 디스크립터에 대해서 공부해 보겠습니다.

 

 

인터럽트 디스크립터란?

 

인터럽트 종류별로 다음과 같은 인터럽트의 세부 속성을 관리하는 자료구조를 인터럽트 디스크립터라고 합니다.

 

인터럽트 핸들러

인터럽트 핸들러 매개변수

논리적인 인터럽트 번호

인터럽트 실행 횟수

 

프로세스의 세부 속성을 표현하는 자료구조가 태스크 디스크립터이듯이 인터럽트에 대한 속성정보를 저장하는 자료구조가 인터럽트 디스크립터인 것입니다. 커널 인터럽트의 세부 함수에서는 인터럽트 디스크립터에 접근해 인터럽트 종류별로 세부적인 처리를 수행합니다. 아래 그림은 인터럽트가 발생했을 때 인터럽트 핸들러를 호출하는 흐름입니다.

 

그림1 인터럽트 디스크립터로 인터럽트 핸들러를 호출하는 과정

 

커널 내부의 인터럽트 함수에서 인터럽트 종류별로 지정된 인터럽트 핸들러를 호출하려면 먼저 인터럽트 디스크립터에 접근해야 합니다. 인터럽트 디스크립터는 인터럽트 핸들러의 주소 정보를 갖고 있는데, 커널에서는 이를 읽어서 인터럽트 핸들러를 호출합니다.

 

인터럽트 디스크립터는 irq_desc 구조체이며 선언 부는 다음과 같습니다.

 

[https://elixir.bootlin.com/linux/v2.6.39.4/source/include/linux/irqdesc.h]

/**
 * struct irq_desc - interrupt descriptor
 * @irq_data:		per irq and chip data passed down to chip functions
 * @timer_rand_state:	pointer to timer rand state struct
 * @kstat_irqs:		irq stats per cpu
 * @handle_irq:		highlevel irq-events handler [if NULL, __do_IRQ()]
 * @action:		the irq action chain
 * @status:		status information
 * @core_internal_state__do_not_mess_with_it: core internal status information
 * @depth:		disable-depth, for nested irq_disable() calls
 * @wake_depth:		enable depth, for multiple set_irq_wake() callers
 * @irq_count:		stats field to detect stalled irqs
 * @last_unhandled:	aging timer for unhandled count
 * @irqs_unhandled:	stats field for spurious unhandled interrupts
 * @lock:		locking for SMP
 * @affinity_notify:	context for notification of affinity changes
 * @pending_mask:	pending rebalanced interrupts
 * @threads_oneshot:	bitfield to handle shared oneshot threads
 * @threads_active:	number of irqaction threads currently running
 * @wait_for_threads:	wait queue for sync_irq to wait for threaded handlers
 * @dir:		/proc/irq/ procfs entry
 * @name:		flow handler name for /proc/interrupts output
 */
struct irq_desc {
	struct irq_data		irq_data;
	struct timer_rand_state *timer_rand_state;
	unsigned int __percpu	*kstat_irqs;
	irq_flow_handler_t	handle_irq;
#ifdef CONFIG_IRQ_PREFLOW_FASTEOI
	irq_preflow_handler_t	preflow_handler;
#endif
	struct irqaction	*action;	/* IRQ action list */
	unsigned int		status_use_accessors;
	unsigned int		core_internal_state__do_not_mess_with_it;
	unsigned int		depth;		/* nested irq disables */
	unsigned int		wake_depth;	/* nested wake enables */
	unsigned int		irq_count;	/* For detecting broken IRQs */
	unsigned long		last_unhandled;	/* Aging timer for unhandled count */
	unsigned int		irqs_unhandled;
	raw_spinlock_t		lock;
#ifdef CONFIG_SMP
	const struct cpumask	*affinity_hint;
	struct irq_affinity_notify *affinity_notify;
#ifdef CONFIG_GENERIC_PENDING_IRQ
	cpumask_var_t		pending_mask;
#endif
#endif
	unsigned long		threads_oneshot;
	atomic_t		threads_active;
	wait_queue_head_t       wait_for_threads;
#ifdef CONFIG_PROC_FS
	struct proc_dir_entry	*dir;
#endif
	const char		*name;
} ____cacheline_internodealigned_in_smp;

'Linux(Centos or RHEL) > RHEL 기초' 카테고리의 다른 글

인터럽트 컨텍스트란?  (0) 2020.04.24
컨텍스트 스위칭과 컨텍스트...?  (0) 2020.04.24
인터럽트 벡터?  (0) 2020.04.23
인터럽트 핸들러?  (0) 2020.04.23
인터럽트?  (0) 2020.04.23