I know what container_of()
does, but I want to obtain a field that is a pointer within some struct like this:
struct A {
int *ptr;
};
void some_func(int *ptr) {
struct A *a = container_of(&ptr, struct A, ptr);
}
But it seems not working. This is compiled successfully, but looks like it produces wrong pointer:
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/init.h>
struct A {
int *ptr;
};
void some_func(int *ptr)
{
struct A *a = container_of(&ptr, struct A, ptr);
if (a)
pr_info("%d", *a->ptr);
else
pr_info("Ooops");
}
int __init m_init(void)
{
int ptr = 10;
struct A a = {.ptr = &ptr};
some_func(&ptr);
return 0;
}
void __exit m_exit(void)
{
}
module_init(m_init);
module_exit(m_exit);
MODULE_LICENSE("GPL");
If I do container_of(ptr, struct A, ptr);
this isn't compiled:
error: static assertion failed: "pointer type mismatch in container_of()"
I guess this is because ptr
is a pointer, not a usual int
, so __same_type
will return false, so make it a pointer.
can anybody help me to fix this?
CodePudding user response:
I will not work. The reason is that ptr
in m_init
is a local variable, so its address &ptr
is meaningless for reconstruction of an address of the other local variable a
.
However, you can replace:
some_func(&ptr);
with
some_func(&a.ptr);
But will require changing some_fun
to take a pointer int*
member of struct A
. So the argument type must be int**
.
void some_func(int **ptr)
{
if (!ptr) {
pr_info("Ooops");
} else {
struct A *a = container_of(ptr, struct A, ptr);
pr_info("%d", *a->ptr);
}
}