![인터럽트 번호에서 인터럽트의 성격을 어떻게 추론할 수 있나요?](https://linux55.com/image/158865/%EC%9D%B8%ED%84%B0%EB%9F%BD%ED%8A%B8%20%EB%B2%88%ED%98%B8%EC%97%90%EC%84%9C%20%EC%9D%B8%ED%84%B0%EB%9F%BD%ED%8A%B8%EC%9D%98%20%EC%84%B1%EA%B2%A9%EC%9D%84%20%EC%96%B4%EB%96%BB%EA%B2%8C%20%EC%B6%94%EB%A1%A0%ED%95%A0%20%EC%88%98%20%EC%9E%88%EB%82%98%EC%9A%94%3F.png)
오래된 컴퓨터를 사용하려고 합니다(HP 파빌리온 엘리트 m9660de). 다음 메시지는 부팅 시 표시되는 첫 번째 메시지입니다(부팅 가능한 USB 스틱 및 새로 설치 모두에서 Ubuntu 및 Fedora).
do_IRQ: 1.55 벡터 irq 핸들러 없음
do_IRQ: 2.55 벡터 irq 핸들러 없음
do_IRQ: 3.55 벡터 irq 핸들러 없음
시작 프로세스는 오랜 시간(예: 15분) 동안 중단되다가 결국 계속됩니다.
나는 이 특정 질문에 대한 지원을 요청하는 것이 아니라 그러한 메시지를 해석하는 방법을 이해하고 싶습니다.
나는 do_IRQ의 커널 코드에서 55가 벡터라는 것을 발견했습니다. 내가 이해한 바에 따르면 이는 인터럽트 핸들러의 주소가 포함된 메모리 위치에 해당하는 인터럽트 수와 비슷합니다.
나는 숫자와 정전으로 이어진 사건 사이에 고정된 대응 관계가 있다고 생각했을 것입니다. 이에 대한 문서는 어디서 찾을 수 있나요? 이것이 Linux 특정인가요, 프로세서 특정인가요, 아니면 마더보드 특정인가요?
답변1
do_IRQ: 1.55 벡터 irq 핸들러 없음
이 메시지는 Linux 커널 소스 파일에서 찾을 수 있으므로 arch/x86/kernel/irq.c
x86 특정 인터럽트 처리에 관한 것입니다.
/*
* do_IRQ handles all normal device IRQ's (the special
* SMP cross-CPU interrupts have their own specific
* handlers).
*/
__visible unsigned int __irq_entry do_IRQ(struct pt_regs *regs)
{
struct pt_regs *old_regs = set_irq_regs(regs);
struct irq_desc * desc;
/* high bit used in ret_from_ code */
unsigned vector = ~regs->orig_ax;
entering_irq();
/* entering_irq() tells RCU that we're not quiescent. Check it. */
RCU_LOCKDEP_WARN(!rcu_is_watching(), "IRQ failed to wake up RCU");
desc = __this_cpu_read(vector_irq[vector]);
if (!handle_irq(desc, regs)) {
ack_APIC_irq();
if (desc != VECTOR_RETRIGGERED && desc != VECTOR_SHUTDOWN) {
pr_emerg_ratelimited("%s: %d.%d No irq handler for vector\n",
__func__, smp_processor_id(),
vector);
} else {
__this_cpu_write(vector_irq[vector], VECTOR_UNUSED);
}
}
exiting_irq();
set_irq_regs(old_regs);
return 1;
}
따라서 첫 번째 숫자(점 앞)는 보고 프로세서의 ID이고 55는 찾은 인터럽트 벡터입니다. IRQ 벡터가 상태에 있으면 VECTOR_SHUTDOWN
이 메시지를 피할 수 있습니다 VECTOR_RETRIGGERED
.
arch/x86/kernel/apic/vector.c
상태 표시 에 따라 의도적으로 지워지는 인터럽트 벡터 VECTOR_SHUTDOWN
입니다(예: 하드웨어 장치가 중지되고 해당 드라이버가 제어된 방식으로 언로드됨).
마지막에 VECTOR_RETRIGGERED
설정되어 있는데 CPU 핫플러깅, 좀 더 구체적으로 CPU를 오프라인으로 표시하는 것과 관련이 있는 것으로 보입니다.fixup_irqs()
arch/x86/kernel/irq.c
따라서 시작 시 일반 PC에서는 두 상태를 모두 사용할 수 없습니다.
인터럽트 벡터 번호와 인터럽트 원인 사이의 고정된 대응에 대한 당신의 생각은 원래 IBM PC의 ISA 버스 아키텍처에 유효했고... 그 후에도 꽤 오랫동안 유효했습니다.
그러나 486 프로세서와 1세대 펜티엄 시대에 APIC(Advanced Programmable Interrupt Controller)가 도입되었습니다. PC 아키텍처에서 여러 프로세서가 공존할 수 있도록 하는 구성 요소 중 하나입니다. 이는 사용 가능한 하드웨어 인터럽트 라인 수를 15개(첫 번째 IBM PC-AT의 것과 같은 8259개의 인터럽트 컨트롤러 쌍)에서 최종적으로 224개의 개별 하드웨어 인터럽트로 늘릴 수 있는 길을 열었습니다. 이를 통해 보다 복잡한 시스템을 설계할 수 있으며 진정한 자체 구성 버스를 달성하는 데 도움이 됩니다.
기본적으로 시스템 펌웨어나 운영 체제는 특정 인터럽트 라인을 사용하도록 버스의 장치를 구성한 다음 인터럽트 신호를 CPU의 사용 가능한 인터럽트 벡터로 라우팅하도록 APIC를 프로그래밍해야 합니다. 이를 위해서는 버스가 실제로 마더보드에 어떻게 연결되어 있는지에 대한 지식이 필요하므로 실제로 이는 거의 전적으로 시스템 펌웨어에 의해 수행되며 특히 펌웨어 버그 패치에 대해 많은 예외가 적용됩니다.
PCI 버스는 원래 인터럽트를 ISA 스타일 인터럽트에 매핑했지만 APIC가 CPU에 통합되면 이 제한이 제거되어 IRQ 대기 시간이 줄어들고 더 복잡한 시스템을 구축할 수 있게 되었습니다. PCI 버스 버전 2.2에는 전용 물리적 인터럽트 라인 없이 개별 하드웨어 인터럽트를 허용하는 MSI(메시지 신호 인터럽트)가 도입되었습니다. PCI Express에서 MSI는 인터럽트를 처리하는 표준 방법이 되었습니다.
따라서...시스템 하드웨어에 IRQ 벡터 55로 라우팅된 활성 인터럽트 소스가 포함되어 있는 것처럼 보이지만 Linux에는 현재 이를 처리할 드라이버가 로드되어 있지 않습니다. PCI 구성 공간은 표준 방식으로 읽을 수 있고 Linux는 이를 읽기 때문에 PCI 버스(또는 PCIe 링크)의 모든 장치를 감지하고 식별해야 하며 해당 인터럽트 구성을 알아야 합니다.
IRQ의 소스가 PCI 장치가 아닐 수도 있습니다.플랫폼 장비, 시스템 칩셋의 일부이거나 일부 비PCI 호환 인터페이스를 사용하여 연결하는 것과 같은 것입니다. 이러한 모든 장치는 펌웨어 ACPI 테이블로 설명되어야 하지만 귀하의 경우 이는 IRQ의 소스가 아닙니다.
내 결론은 이것이 아마도 펌웨어 버그일 것이라는 것입니다. HP가 시스템에 대한 BIOS 업데이트를 제공하는지 확인하십시오. (현재 HP Pavilion Elite m9660de에 대한 지원 다운로드 페이지가 로딩되지 않는 것으로 보입니다.)
~에 따르면우분투 포럼의 이 스레드pci=nomsi,noaer
VIA 칩셋의 하드웨어 버그일 수도 있습니다. 시스템에 이 칩셋이 있는 경우 GRUB에 부팅 옵션을 추가하면 문제가 해결될 수 있습니다.
현재 커널이 debugfs
CONFIG_GENERIC_IRQ_DEBUGFS 커널 옵션을 지원하고 활성화하는 경우 루트로 다음 명령을 사용하여 IRQ 벡터 55 상태에 대한 광범위한 정보를 얻을 수 있습니다.
mount -t debugfs none /sys/kernel/debug
grep "Vector.*55" /sys/kernel/debug/irq/irqs/*
그러면 해당 디렉토리의 어떤 파일에 "Vector:55"가 언급되어 있는지 알 수 있습니다. 이 파일을 읽으면 커널이 이 인터럽트 벡터에 대해 알고 있는 모든 것을 알 수 있습니다.