外面有东西吗?就像top是为了ps
当 Linux 系统中发生页面错误时,中断处理程序必须找出页面错误发生的原因。但是怎么样?
我正在尝试使用较旧的 PC(HP Pavilion Elite m9660de)启动/安装 Linux 以进行学习。以下消息是启动时显示的第一件事(Ubuntu 和 Fedora,都来自可启动的 USB 记忆棒和全新安装):
do_IRQ:1.55 没有向量的 irq 处理程序
do_IRQ:2.55 没有向量的 irq 处理程序
do_IRQ: 3.55 没有向量的 irq 处理程序
引导过程将在那里停滞很长时间(如 15 分钟),并最终继续。
我不是要求获得对这个具体问题的支持,而是要了解如何解释这样的消息。
我在 do_IRQ 的内核代码中发现 55 是一个向量。据我了解,这或多或少是一个中断的数量,对应于包含中断处理程序地址的内存位置。
我原以为这些数字与导致中断的事件之间存在固定的对应关系。我在哪里可以找到这方面的文档?这是特定于 Linux、特定于处理器还是特定于主板?
在 GNOME 下运行的任何终端中,如果我按Ctrl+ C,我只会看到一个问号。同去的Ctrl+ Z。的输出stty -a | grep intr是:
intr = ^C; quit = ^\; erase = ^?; kill = ^U; eof = ^D; eol = M-^?; eol2 = M-^?;
Run Code Online (Sandbox Code Playgroud)
我可以在所有其他 tty 下(X 之外)使用该序列,也可以将其用于其他用户;只有一名用户受到影响。我怎样才能解决这个问题?
我试图以这样一种方式处理 SIGINT/CTRL+C 中断,如果用户不小心按下了 ctrl-c,他会收到一条消息提示,“你想退出吗?(y/n)”。如果他输入 yes,则退出脚本。如果否,则从中断发生的地方继续。基本上,我需要 Ctrl-C 与 Ctrl-Z/SINTSTP 类似,但方式略有不同。我尝试了各种方法来实现这一点,但没有得到预期的结果。以下是我尝试过的几个场景。
情况1
脚本:play.sh
#!/bin/sh
function stop()
{
while true; do
read -rep $'\nDo you wish to stop playing?(y/n)' yn
case $yn in
[Yy]* ) echo "Thanks for playing !!!"; exit 1;;
[Nn]* ) break;;
* ) echo "Please answer (y/n)";;
esac
done
}
trap 'stop' SIGINT
echo "going to sleep"
for i in {1..100}
do
echo "$i"
sleep 3
done
echo "end of sleep"
Run Code Online (Sandbox Code Playgroud)
当我运行上面的脚本时,我得到了预期的结果。
输出:
$ play.sh
going to sleep
1 …Run Code Online (Sandbox Code Playgroud) 给定接口名称(例如 eth0),以编程方式确定与网络接口关联的 IRQ 的最可靠方法是什么?
我对尽力而为的方法没问题,但我希望它适用于各种驱动程序/配置(即没有对每个驱动程序进行特殊处理),并且我想避免误报。我还想避免违反此处概述的与 sysfs 交互的规则,但我可以在必要时打破它们。我将在下面的示例中打破它们。
解析/proc/interrupts并不理想,因为与 IRQ 关联的名称是特定于驱动程序的,并且不可靠,因为没有什么可以阻止两个设备具有相同名称的 IRQ。
如果我可以执行以下操作,那就太好了:
$ ls /sys/class/net/eth2/device/msi_irqs | cat /sys/class/net/eth2/device/irq
61 62 63
Run Code Online (Sandbox Code Playgroud)
我已经使用/proc/interrupts.
但这并不适用于所有驱动程序。感兴趣的 IRQ 文件位于不同的位置,或者无处可寻。
vmxnet3 接口:
$ readlink -e /sys/class/net/eth2
/sys/devices/pci0000:00/0000:00:16.0/0000:0b:00.0/net/eth2
$ ls $(readlink -e /sys/class/net/eth2)/../../msi_irqs
61 62 63
Run Code Online (Sandbox Code Playgroud)
感兴趣的 msi_irqs 是从 /sys/class/net/eth2 符号链接向上的两个目录。msi_irqs 三个目录上面都跟我无关。
虚拟界面:
$ readlink -e /sys/class/net/eth1
/sys/devices/pci0000:00/0000:00:03.0/virtio0/net/eth1
ls $(readlink -e /sys/class/net/eth1)/../../../msi_irqs
26 27 28
Run Code Online (Sandbox Code Playgroud)
感兴趣的 msi_irqs 是从 /sys/class/net/eth1 符号链接向上的三个目录。此层次结构中没有其他 msi_irqs 文件。
hv_netvsc 接口:
$ readlink -e /sys/class/net/eth0
/sys/devices/LNXSYSTM:00/LNXSYBUS:00/PNP0A03:00/device:07/VMBus:00/vmbus_0_11/net/eth0
Run Code Online (Sandbox Code Playgroud)
IRQ …
我正在阅读APUE,中断系统调用一章让我感到困惑。
我想根据书中写下我的理解,请指正。
早期 UNIX 系统的一个特点是,如果进程在“慢”系统调用中被阻塞时捕获到信号,则系统调用将被中断。系统调用返回错误并
errno设置为EINTR。这是在假设发生信号并且进程捕获它之后完成的,很有可能发生了一些应该唤醒被阻塞的系统调用的事情。
所以说早期的UNIX 系统有一个特性:如果我的程序使用系统调用,它会被中断/停止,如果程序在任何时候捕捉到信号。(默认处理程序也算作捕获吗?)
例如,如果我有一个read系统调用,它读取 10GB 数据,当它正在读取时,我发送任何一个信号(例如kill -SIGUSR1 pid),然后read将失败并返回。
为了防止应用程序不得不处理中断的系统调用,4.2BSD 引入了某些中断系统调用的自动重启。被自动重新启动的系统调用
ioctl,read,readv,write,writev,wait,和waitpid。正如我们所提到的,这些功能中的前五个功能只有在它们在慢速设备上运行时才会被信号中断;wait并且waitpid在捕获到信号时总是被中断。由于这会导致一些应用程序出现问题,如果操作被中断,则不希望操作重新启动,4.3BSD 允许进程在每个信号的基础上禁用此功能。
所以在引入自动重启之前,我不得不自己处理中断的系统调用。我需要编写如下代码:
中断系统调用的问题在于我们现在必须显式地处理错误返回。典型的代码序列(假设读取操作并假设我们想要重新启动读取,即使它被中断)将是:
again:
if ((n = read(fd, buf, BUFFSIZE)) < 0) {
if (errno == EINTR)
goto again; /* just an interrupted system call */
/* handle other errors …Run Code Online (Sandbox Code Playgroud) 我一直在阅读Linux Kernel Development,但有一些事情对我来说并不完全清楚——当硬件触发中断时,决定哪个 CPU 运行中断处理逻辑的标准是什么?
我可以想象它必须始终与引发 IO 请求的 CPU 相同,但由于线程用于所有目的,现在正在休眠,因此这样做并没有多大意义。
另一方面,可能存在需要引发的定时中断(例如,对于调度程序)。在 SMP 系统上,它们总是在同一个核心上提升(比方说,#0)还是它们几乎总是在任何核心上提升?
它实际上是如何工作的?
谢谢
我必须永久更改中断的 smp_affinity。服务器重启时需要执行以下代码:
echo "1" > /proc/irq/152/smp_affinity_list
echo "2" > /proc/irq/151/smp_affinity_list
echo "3" > /proc/irq/150/smp_affinity_list
echo "4" > /proc/irq/149/smp_affinity_list
echo "5" > /proc/irq/148/smp_affinity_list
echo "6" > /proc/irq/147/smp_affinity_list
echo "7" > /proc/irq/146/smp_affinity_list
echo "8" > /proc/irq/145/smp_affinity_list
echo "9" > /proc/irq/144/smp_affinity_list
echo "10" > /proc/irq/143/smp_affinity_list
echo "11" > /proc/irq/142/smp_affinity_list
echo "12" > /proc/irq/141/smp_affinity_list
echo "13" > /proc/irq/140/smp_affinity_list
echo "14" > /proc/irq/139/smp_affinity_list
echo "15" > /proc/irq/138/smp_affinity_list
echo "16" > /proc/irq/137/smp_affinity_list
Run Code Online (Sandbox Code Playgroud)
我已将这些行添加到 /etc/rc.local 文件中,但更改并未应用于系统。我还添加了 echo "test" > /root/test ,它被正确执行,所以 rc.local 文件被执行。系统运行的是 Debian 6.0。
我正在从 bash 脚本启动两个子进程并使用wait命令等待两者完成:
./proc1 &
pid1=$!
echo "started proc1: ${pid1}"
./proc2 &
pid2=$!
echo "started proc2: ${pid2}"
echo -n "working..."
wait $pid1 $pid2
echo " done"
Run Code Online (Sandbox Code Playgroud)
这个脚本在正常情况下工作正常:它等待两个进程完成并在它之后退出。但有时我需要停止这个脚本(使用Ctrl+C)。但是当我停止它时,子进程不会被中断。我怎样才能用主脚本完全杀死它们?