mbigen的domain匹配
来源:互联网 发布:李雨桐和薛之谦 知乎 编辑:程序博客网 时间:2024/04/30 14:40
在mbigen_device_probe->mbigen_acpi_create_domain->platform_msi_create_device_domain
domain = platform_msi_create_device_domain(&pdev->dev, num_msis,
mbigen_write_msg,
&mbigen_domain_ops,
mgn_chip);
注意在调用platform_msi_create_device_domain 的时候会传递一个mbigen_domain_ops
static struct irq_domain_ops mbigen_domain_ops = {
.translate = mbigen_domain_translate,
.alloc = mbigen_irq_domain_alloc,
.free = irq_domain_free_irqs_common,
};
随后platform_msi_create_device_domain->irq_domain_create_hierarchy->irq_domain_create_linear->__irq_domain_add
struct irq_domain *__irq_domain_add(struct fwnode_handle *fwnode, int size,
irq_hw_number_t hwirq_max, int direct_max,
const struct irq_domain_ops *ops,
void *host_data)
{
struct device_node *of_node = to_of_node(fwnode);
struct irq_domain *domain;
domain = kzalloc_node(sizeof(*domain) + (sizeof(unsigned int) * size),
GFP_KERNEL, of_node_to_nid(of_node));
if (WARN_ON(!domain))
return NULL;
of_node_get(of_node);
/* Fill structure */
INIT_RADIX_TREE(&domain->revmap_tree, GFP_KERNEL);
domain->ops = ops;
domain->host_data = host_data;
domain->fwnode = fwnode;
domain->hwirq_max = hwirq_max;
domain->revmap_size = size;
domain->revmap_direct_max_irq = direct_max;
irq_domain_check_hierarchy(domain);
mutex_lock(&irq_domain_mutex);
list_add(&domain->link, &irq_domain_list);
mutex_unlock(&irq_domain_mutex);
pr_debug("Added domain %s\n", domain->name);
return domain;
}
在__irq_domain_add 中我们会初始化一个irq_domain *domain,并将其添加到irq_domain_list,而irq_domain_list是一个全局的静态list.总结一下mbigen 这个模块走的最重要的事情就是初始化了一个irq_domain而已
那irq_domain_list 中应该包含很多domain,设备具体要用哪一个domain是在哪里决定的呢?
以下面的函数为例
int acpi_register_gsi(struct device *dev, u32 gsi, int trigger,
int polarity)
{
struct irq_fwspec fwspec;
struct acpi_device *adev = dev ? to_acpi_device(dev) : NULL;
if (adev && is_acpi_device_node(&adev->fwnode) &&
adev->interrupt_producer)
/* devices in DSDT connecting to spefic interrupt producer */
fwspec.fwnode = adev->interrupt_producer;
else if (acpi_gsi_domain_id)
/* devices connecting to gicd in default */
fwspec.fwnode = acpi_gsi_domain_id;
else {
pr_warn("GSI: No registered irqchip, giving up\n");
return -EINVAL;
}
fwspec.param[0] = gsi;
fwspec.param[1] = acpi_dev_get_irq_type(trigger, polarity);
fwspec.param_count = 2;
return irq_create_fwspec_mapping(&fwspec);
}
acpi_register_gsi 中初始化了一个irq_fwspec。
unsigned int irq_create_fwspec_mapping(struct irq_fwspec *fwspec)
{
struct irq_domain *domain;
struct irq_data *irq_data;
irq_hw_number_t hwirq;
unsigned int type = IRQ_TYPE_NONE;
int virq;
if (fwspec->fwnode) {
domain = irq_find_matching_fwspec(fwspec, DOMAIN_BUS_WIRED);
if (!domain)
domain = irq_find_matching_fwspec(fwspec, DOMAIN_BUS_ANY);
} else {
domain = irq_default_domain;
}
}
由于fwspec->fwnode 肯定不为NULL,因此调用irq_find_matching_fwspec
struct irq_domain *irq_find_matching_fwspec(struct irq_fwspec *fwspec,
enum irq_domain_bus_token bus_token)
{
struct irq_domain *h, *found = NULL;
struct fwnode_handle *fwnode = fwspec->fwnode;
int rc;
/* We might want to match the legacy controller last since
* it might potentially be set to match all interrupts in
* the absence of a device node. This isn't a problem so far
* yet though...
*
* bus_token == DOMAIN_BUS_ANY matches any domain, any other
* values must generate an exact match for the domain to be
* selected.
*/
mutex_lock(&irq_domain_mutex);
list_for_each_entry(h, &irq_domain_list, link) {
if (h->ops->select && fwspec->param_count)
rc = h->ops->select(h, fwspec, bus_token);
else if (h->ops->match)
rc = h->ops->match(h, to_of_node(fwnode), bus_token);
else
rc = ((fwnode != NULL) && (h->fwnode == fwnode) &&
((bus_token == DOMAIN_BUS_ANY) ||
(h->bus_token == bus_token)));
if (rc) {
found = h;
break;
}
}
mutex_unlock(&irq_domain_mutex);
return found;
}
在irq_find_matching_fwspec 中我们以mbigen的struct irq_domain_ops mbigen_domain_ops为例,由于mbigen_domain_ops为例的select和match函数为NULL,因此在irq_find_matching_fwspec走最后的else。由于在mbigen中初始化domain的时候并没有定义bus_token,因此h->bus_token=0,而irq_create_fwspec_mapping 中bus_token==DOMAIN_BUS_WIRED,因此else的条件也就不满足。因此如果要使用mbigen这个domain除了硬件要挂在mbigen下面外,其bus_token 应该要等于DOMAIN_BUS_ANY
domain = platform_msi_create_device_domain(&pdev->dev, num_msis,
mbigen_write_msg,
&mbigen_domain_ops,
mgn_chip);
注意在调用platform_msi_create_device_domain 的时候会传递一个mbigen_domain_ops
static struct irq_domain_ops mbigen_domain_ops = {
.translate = mbigen_domain_translate,
.alloc = mbigen_irq_domain_alloc,
.free = irq_domain_free_irqs_common,
};
随后platform_msi_create_device_domain->irq_domain_create_hierarchy->irq_domain_create_linear->__irq_domain_add
struct irq_domain *__irq_domain_add(struct fwnode_handle *fwnode, int size,
irq_hw_number_t hwirq_max, int direct_max,
const struct irq_domain_ops *ops,
void *host_data)
{
struct device_node *of_node = to_of_node(fwnode);
struct irq_domain *domain;
domain = kzalloc_node(sizeof(*domain) + (sizeof(unsigned int) * size),
GFP_KERNEL, of_node_to_nid(of_node));
if (WARN_ON(!domain))
return NULL;
of_node_get(of_node);
/* Fill structure */
INIT_RADIX_TREE(&domain->revmap_tree, GFP_KERNEL);
domain->ops = ops;
domain->host_data = host_data;
domain->fwnode = fwnode;
domain->hwirq_max = hwirq_max;
domain->revmap_size = size;
domain->revmap_direct_max_irq = direct_max;
irq_domain_check_hierarchy(domain);
mutex_lock(&irq_domain_mutex);
list_add(&domain->link, &irq_domain_list);
mutex_unlock(&irq_domain_mutex);
pr_debug("Added domain %s\n", domain->name);
return domain;
}
在__irq_domain_add 中我们会初始化一个irq_domain *domain,并将其添加到irq_domain_list,而irq_domain_list是一个全局的静态list.总结一下mbigen 这个模块走的最重要的事情就是初始化了一个irq_domain而已
那irq_domain_list 中应该包含很多domain,设备具体要用哪一个domain是在哪里决定的呢?
以下面的函数为例
int acpi_register_gsi(struct device *dev, u32 gsi, int trigger,
int polarity)
{
struct irq_fwspec fwspec;
struct acpi_device *adev = dev ? to_acpi_device(dev) : NULL;
if (adev && is_acpi_device_node(&adev->fwnode) &&
adev->interrupt_producer)
/* devices in DSDT connecting to spefic interrupt producer */
fwspec.fwnode = adev->interrupt_producer;
else if (acpi_gsi_domain_id)
/* devices connecting to gicd in default */
fwspec.fwnode = acpi_gsi_domain_id;
else {
pr_warn("GSI: No registered irqchip, giving up\n");
return -EINVAL;
}
fwspec.param[0] = gsi;
fwspec.param[1] = acpi_dev_get_irq_type(trigger, polarity);
fwspec.param_count = 2;
return irq_create_fwspec_mapping(&fwspec);
}
acpi_register_gsi 中初始化了一个irq_fwspec。
unsigned int irq_create_fwspec_mapping(struct irq_fwspec *fwspec)
{
struct irq_domain *domain;
struct irq_data *irq_data;
irq_hw_number_t hwirq;
unsigned int type = IRQ_TYPE_NONE;
int virq;
if (fwspec->fwnode) {
domain = irq_find_matching_fwspec(fwspec, DOMAIN_BUS_WIRED);
if (!domain)
domain = irq_find_matching_fwspec(fwspec, DOMAIN_BUS_ANY);
} else {
domain = irq_default_domain;
}
}
由于fwspec->fwnode 肯定不为NULL,因此调用irq_find_matching_fwspec
struct irq_domain *irq_find_matching_fwspec(struct irq_fwspec *fwspec,
enum irq_domain_bus_token bus_token)
{
struct irq_domain *h, *found = NULL;
struct fwnode_handle *fwnode = fwspec->fwnode;
int rc;
/* We might want to match the legacy controller last since
* it might potentially be set to match all interrupts in
* the absence of a device node. This isn't a problem so far
* yet though...
*
* bus_token == DOMAIN_BUS_ANY matches any domain, any other
* values must generate an exact match for the domain to be
* selected.
*/
mutex_lock(&irq_domain_mutex);
list_for_each_entry(h, &irq_domain_list, link) {
if (h->ops->select && fwspec->param_count)
rc = h->ops->select(h, fwspec, bus_token);
else if (h->ops->match)
rc = h->ops->match(h, to_of_node(fwnode), bus_token);
else
rc = ((fwnode != NULL) && (h->fwnode == fwnode) &&
((bus_token == DOMAIN_BUS_ANY) ||
(h->bus_token == bus_token)));
if (rc) {
found = h;
break;
}
}
mutex_unlock(&irq_domain_mutex);
return found;
}
在irq_find_matching_fwspec 中我们以mbigen的struct irq_domain_ops mbigen_domain_ops为例,由于mbigen_domain_ops为例的select和match函数为NULL,因此在irq_find_matching_fwspec走最后的else。由于在mbigen中初始化domain的时候并没有定义bus_token,因此h->bus_token=0,而irq_create_fwspec_mapping 中bus_token==DOMAIN_BUS_WIRED,因此else的条件也就不满足。因此如果要使用mbigen这个domain除了硬件要挂在mbigen下面外,其bus_token 应该要等于DOMAIN_BUS_ANY
0 0
- mbigen的domain匹配
- mbigen
- 在shiro当设置sessionIdCookie配置的domain和访问url不匹配时,每次请求都会重新生成session
- 有了自己的domain~~
- Weblogic Domain的卸载
- cookie 的domain属性
- 有关Weblogic的domain
- 创建新的domain
- domain的一些理解
- GlassFish的domain管理
- Odoo的Domain (一)
- cookie的domain实战
- domain
- domain
- Basic验证的Domain处理
- link和domain的区别
- Domain testing 云里雾里的概念
- [HTML] document domain 的说明
- APP安全报告第十期:部分美图类APP存在窃取用户隐私数据的风险!
- <meta name="viewport" content="width=device-width, initial-scale=1">
- 计时器问题的区别和清除
- linux irqdebug
- java NEW一个对象之后加入大括号
- mbigen的domain匹配
- oracle 数据库恢复
- ionic用过的那些插件
- java异常 -The method getTextContent() is undefined for the type Element
- OpenAPI Specification 2.0
- 安装Tomcat
- CF的高可用
- 5-4 统计学生平均成绩与及格人数 (5分)
- <meta http-equiv="X-UA-Compatible" content="IE=edge">