只能实例化 1 个通用 uio 设备
Can only instantiate 1 generic-uio device
我正在尝试使用 uio_pdrv_genirq 驱动程序向用户空间公开中断。但是我只能在设备树中实例化 1 个设备,所有后续设备都无法通过探测。
系统是zynq-7000,内核版本是3.9.0-xilinx.
设备树:
/ {
...
amba@0 {
...
gic: intc@f8f01000 {
interrupt-controller;
compatible = "arm,cortex-a9-gic";
#interrupt-cells = <3>;
reg = <0xf8f01000 0x1000>,
<0xf8f00100 0x0100>;
};
interrupt_91@0x43C90000 {
compatible = "generic-uio";
reg = < 0x43C90000 0x1000 >;
interrupts = < 0 59 1 >; //add 32 to get the interrupt number
interrupt-parent = <&gic>;
} ;
interrupter_90@0x43CA0000 {
compatible = "generic-uio";
reg = < 0x43CA0000 0x1000 >;
interrupts = < 0 58 1 >; //add 32 to get the interrupt number
interrupt-parent = <&gic>;
} ;
...
};
dmesg 输出:
dmesg | grep uio
uio_pdrv_genirq 43ca0000.interrupter_90: unable to register uio device
uio_pdrv_genirq: probe of 43ca0000.interrupter_90 failed with error 1
内核配置:
CONFIG_UIO=y
# CONFIG_UIO_CIF is not set
CONFIG_UIO_PDRV_GENIRQ=y
# CONFIG_UIO_DMEM_GENIRQ is not set
# CONFIG_UIO_AEC is not set
# CONFIG_UIO_SERCOS3 is not set
# CONFIG_UIO_PCI_GENERIC is not set
# CONFIG_UIO_NETX is not set
我确定我早些时候在 Zedboard 上完成了这个工作,我不知道这里可能有什么问题。
好的,原来是我使用的内核源代码有问题。
行数:
if (ret)
goto err_get_minor;
在 drivers/uio/uio.c 和行中:
if (ret) {
dev_err(&pdev->dev, "unable to register uio device\n");
goto bad1;
}
in drivers/uio/uio_pdrv_genirq.c 都必须更改,以便 if 语句读取 if (ret < 0)
.
原因是 uio_get_minor
函数(其 return 值,ret,他们正在使用)returns 分配的次要编号。这是 0, 1, 2, ..., 等等。很明显,第一个设备(minor id = 0)注册正常,但第二个设备(minor id = 1)失败了。这解释了错误消息 "failed with error 1" 这是次要 ID 而不是我最初假设的 EPERM。
我使用的存储库是 https://github.com/Trenz-Electronic/linux-te-3.9 以供将来参考。
编辑:实际上,主线内核中存在同样的问题,我会post一个补丁。
我正在尝试使用 uio_pdrv_genirq 驱动程序向用户空间公开中断。但是我只能在设备树中实例化 1 个设备,所有后续设备都无法通过探测。 系统是zynq-7000,内核版本是3.9.0-xilinx.
设备树:
/ {
...
amba@0 {
...
gic: intc@f8f01000 {
interrupt-controller;
compatible = "arm,cortex-a9-gic";
#interrupt-cells = <3>;
reg = <0xf8f01000 0x1000>,
<0xf8f00100 0x0100>;
};
interrupt_91@0x43C90000 {
compatible = "generic-uio";
reg = < 0x43C90000 0x1000 >;
interrupts = < 0 59 1 >; //add 32 to get the interrupt number
interrupt-parent = <&gic>;
} ;
interrupter_90@0x43CA0000 {
compatible = "generic-uio";
reg = < 0x43CA0000 0x1000 >;
interrupts = < 0 58 1 >; //add 32 to get the interrupt number
interrupt-parent = <&gic>;
} ;
...
};
dmesg 输出:
dmesg | grep uio
uio_pdrv_genirq 43ca0000.interrupter_90: unable to register uio device
uio_pdrv_genirq: probe of 43ca0000.interrupter_90 failed with error 1
内核配置:
CONFIG_UIO=y
# CONFIG_UIO_CIF is not set
CONFIG_UIO_PDRV_GENIRQ=y
# CONFIG_UIO_DMEM_GENIRQ is not set
# CONFIG_UIO_AEC is not set
# CONFIG_UIO_SERCOS3 is not set
# CONFIG_UIO_PCI_GENERIC is not set
# CONFIG_UIO_NETX is not set
我确定我早些时候在 Zedboard 上完成了这个工作,我不知道这里可能有什么问题。
好的,原来是我使用的内核源代码有问题。
行数:
if (ret)
goto err_get_minor;
在 drivers/uio/uio.c 和行中:
if (ret) {
dev_err(&pdev->dev, "unable to register uio device\n");
goto bad1;
}
in drivers/uio/uio_pdrv_genirq.c 都必须更改,以便 if 语句读取 if (ret < 0)
.
原因是 uio_get_minor
函数(其 return 值,ret,他们正在使用)returns 分配的次要编号。这是 0, 1, 2, ..., 等等。很明显,第一个设备(minor id = 0)注册正常,但第二个设备(minor id = 1)失败了。这解释了错误消息 "failed with error 1" 这是次要 ID 而不是我最初假设的 EPERM。
我使用的存储库是 https://github.com/Trenz-Electronic/linux-te-3.9 以供将来参考。
编辑:实际上,主线内核中存在同样的问题,我会post一个补丁。