가끔 인터럽트 핸들러의 처리 시간이 조금 더 정확히 보고 싶을 때가 있습니다.
이때, 다음과 같은 패치 코드를 적용하면 인터럽트 핸들러의 실행 시간을 측정할 수 있습니다.
패치 코드는 다음과 같습니다.
diff --git a/drivers/mailbox/bcm2835-mailbox.c b/drivers/mailbox/bcm2835-mailbox.c
index a03aeed..e353beb 100644
--- a/drivers/mailbox/bcm2835-mailbox.c
+++ b/drivers/mailbox/bcm2835-mailbox.c
@@ -72,17 +72,29 @@ static struct bcm2835_mbox *bcm2835_link_mbox(struct mbox_chan *link)
return container_of(link->mbox, struct bcm2835_mbox, controller);
}
+#define HANDLE_TIME 100
+
static irqreturn_t bcm2835_mbox_irq(int irq, void *dev_id)
{
+ u64 diff, start_time, curr_time;
struct bcm2835_mbox *mbox = dev_id;
struct device *dev = mbox->controller.dev;
struct mbox_chan *link = &mbox->controller.chans[0];
+ start_time = sched_clock();
while (!(readl(mbox->regs + MAIL0_STA) & ARM_MS_EMPTY)) {
u32 msg = readl(mbox->regs + MAIL0_RD);
dev_dbg(dev, "Reply 0x%08X\n", msg);
mbox_chan_received_data(link, &msg);
}
+
+ curr_time = sched_clock();
+ diff = curr_time - start_time;
+
+ if (diff > HANDLE_TIME)
+ trace_printk("interrupt: elapsed: %llu, start: %llu \n",
+ diff, start_time);
+
return IRQ_HANDLED;
}
코드 내용은 너무 간단합니다. 나노초 단위의 시간 정보를 반환하는 sched_clock() 함수를 사용해서
실행 시각을 계산하는 코드입니다. 인터럽트 함수의 실행 시간 정보를 저장하는 diff 지역 변수를 ftrace로출력합니다.
참고로 인터럽트 핸들러가 실행될 때는 인터럽트 컨텍스트입니다. 빨리 코드가 실행돼야 하니 printk() 함수를 써서 커널 로그를 출력하는 것은 자제해야 합니다.
Austin Kim, 궁금한 점이 있으면 댓글로 질문을 남겨주세요.
'[Debugging] Tips' 카테고리의 다른 글
[리눅스커널] 안드로이드/라즈베리 파이 부팅 실패 100% 해결하는 디버깅 패치 (0) | 2023.05.04 |
---|---|
[TRACE32] 유저 공간 콜스택 복원하기 - ARMv8(Aarch64) (0) | 2023.05.04 |
[리눅스커널] 커널 동적 타이머를 사용해 실행 시각을 측정해보기 (0) | 2023.05.04 |
[리눅스커널] 크래시 유틸리티: files -p '아이노드 주소' + files -d '덴트리 주소' 디버깅 (0) | 2023.05.04 |
[TRACE32] gcore 크래시 유틸리티로 유저 프로세스의 콜스택 보기 (0) | 2023.05.04 |