This adds suport for kernel 3.2.
Signed-off-by: Hauke Mehrtens <[email protected]>
---
include/linux/compat-3.2.h | 17 -----------------
include/linux/compat-3.3.h | 16 ++++++++++++++++
2 files changed, 16 insertions(+), 17 deletions(-)
diff --git a/include/linux/compat-3.2.h b/include/linux/compat-3.2.h
index ceaaecc..db0f648 100644
--- a/include/linux/compat-3.2.h
+++ b/include/linux/compat-3.2.h
@@ -8,23 +8,6 @@
#include <linux/skbuff.h>
#include <linux/dma-mapping.h>
-/*
- * This is not part of The 2.6.37 kernel yet but we
- * we use it to optimize the backport code we
- * need to implement. Instead of using ifdefs
- * to check what version of the check we use
- * we just replace all checks on current code
- * with this. I'll submit this upstream too, that
- * way all we'd have to do is to implement this
- * for older kernels, then we would not have to
- * edit the upstrema code for backport efforts.
- */
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36))
-#define br_port_exists(dev) (dev->priv_flags & IFF_BRIDGE_PORT)
-#else
-#define br_port_exists(dev) (dev->br_port)
-#endif
-
#define PMSG_IS_AUTO(msg) (((msg).event & PM_EVENT_AUTO) != 0)
/**
diff --git a/include/linux/compat-3.3.h b/include/linux/compat-3.3.h
index 2e1e6d3..4e96ddc 100644
--- a/include/linux/compat-3.3.h
+++ b/include/linux/compat-3.3.h
@@ -8,6 +8,22 @@
/* include to override NL80211_FEATURE_SK_TX_STATUS */
#include <linux/nl80211.h>
+/*
+ * This is not part of The 2.6.37 kernel yet but we
+ * we use it to optimize the backport code we
+ * need to implement. Instead of using ifdefs
+ * to check what version of the check we use
+ * we just replace all checks on current code
+ * with this. I'll submit this upstream too, that
+ * way all we'd have to do is to implement this
+ * for older kernels, then we would not have to
+ * edit the upstrema code for backport efforts.
+ */
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36))
+#define br_port_exists(dev) (dev->priv_flags & IFF_BRIDGE_PORT)
+#else
+#define br_port_exists(dev) (dev->br_port)
+#endif
static inline void skb_complete_wifi_ack(struct sk_buff *skb, bool acked)
{
--
1.7.4.1
On 11/17/2011 11:27 PM, Johannes Berg wrote:
> On Thu, 2011-11-17 at 22:23 +0100, Hauke Mehrtens wrote:
>
>> +#undef module_exit
>> +#define module_exit(exitfn) \
>
>> + static inline exitcall_t __exittest(void) \
>> + { return exitfn; } \
>
> This is not necessary since the exitfn() below will already create a
> compile error if you try module_exit(no_such_function).
This check is not needed, I will remove it. We get the code from the
kernel and it should compile. Most of the tests this function does are
also done by our real function.
>
>> + void __exit __exit_compat(void) \
>> + { \
>
> Shouldn't that be static?
Yes it also works when it is static I changed that.
>
> johannes
>
>
Hauke
On Thu, 2011-11-17 at 22:23 +0100, Hauke Mehrtens wrote:
> +#undef module_exit
> +#define module_exit(exitfn) \
> + static inline exitcall_t __exittest(void) \
> + { return exitfn; } \
This is not necessary since the exitfn() below will already create a
compile error if you try module_exit(no_such_function).
> + void __exit __exit_compat(void) \
> + { \
Shouldn't that be static?
johannes
On Thu, Nov 17, 2011 at 3:05 PM, Hauke Mehrtens <[email protected]> wrote:
> This adds a nested function everywhere kfree_rcu() was called. This
> function frees the memory and is given as a function to call_rcu().
> The kfree_rcu define was made by Johannes Berg.
> The rcu callback could happen every time also after the module was
> unloaded and this will cause problems.
> A rcu_barrier() was added into every module_exit so that this will not
> be called after the module was unloaded.
>
> The define overwriting module_exit is based on the original module_exit
> which looks like this:
> /* This is only required if you want to be unloadable. */
> /#define module_exit(exitfn) \
> static inline exitcall_t __exittest(void) \
> { return exitfn; } \
> void cleanup_module(void) __attribute__((alias(#exitfn)));
>
> We replaced the call to the actual function exitfn() with a call to our
> function which calls the original exitfn() and then rcu_barrier()
>
> As a module will not be unloaded that ofter it should not have a big
> performance impact when rcu_barrier() is called on every module exit,
> also when no kfree_rcu() backport is used in that module.
>
> Signed-off-by: Hauke Mehrtens <[email protected]>
> CC: Johannes Berg <[email protected]>
> ---
> v2: remove compile check for exitfn
> make function static
Wow, that's pretty fucking hairy, good stuff though, thanks! Applied and pushed!
Luis
Signed-off-by: Hauke Mehrtens <[email protected]>
---
include/linux/compat-3.3.h | 2 ++
1 files changed, 2 insertions(+), 0 deletions(-)
diff --git a/include/linux/compat-3.3.h b/include/linux/compat-3.3.h
index 4e96ddc..9383a6e 100644
--- a/include/linux/compat-3.3.h
+++ b/include/linux/compat-3.3.h
@@ -31,6 +31,8 @@ static inline void skb_complete_wifi_ack(struct sk_buff *skb, bool acked)
}
#define NL80211_FEATURE_SK_TX_STATUS 0
+typedef u32 netdev_features_t;
+
#endif /* (LINUX_VERSION_CODE < KERNEL_VERSION(3,3,0)) */
#endif /* LINUX_3_3_COMPAT_H */
--
1.7.4.1
This adds a nested function everywhere kfree_rcu() was called. This
function frees the memory and is given as a function to call_rcu().
The kfree_rcu define was mad by Johannes Berg.
The rcu callback could happen every time also after the module was
unloaded and this will cause problems.
A rcu_barrier() was added into every module_exit so that this will not
be called after the module was unloaded.
The define overwriting module_exit is based on the original module_exit
which looks like this:
/* This is only required if you want to be unloadable. */
/#define module_exit(exitfn) \
static inline exitcall_t __exittest(void) \
{ return exitfn; } \
void cleanup_module(void) __attribute__((alias(#exitfn)));
We replaced the call to the actual function exitfn() with a call to our
function which calls the original exitfn() and then rcu_barrier()
As a module will not be unloaded that ofter it should not have a big
performance impact when rcu_barrier() is called on every module exit,
also when no kfree_rcu() backport is used in that module.
Signed-off-by: Hauke Mehrtens <[email protected]>
CC: Johannes Berg <[email protected]>
---
include/linux/compat-3.0.h | 48 ++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 48 insertions(+), 0 deletions(-)
diff --git a/include/linux/compat-3.0.h b/include/linux/compat-3.0.h
index 8c8720e..56639fd 100644
--- a/include/linux/compat-3.0.h
+++ b/include/linux/compat-3.0.h
@@ -5,6 +5,8 @@
#if (LINUX_VERSION_CODE < KERNEL_VERSION(3,0,0))
+#include <linux/rcupdate.h>
+
/*
* since commit 1c5cae815d19ffe02bdfda1260949ef2b1806171
* "net: call dev_alloc_name from register_netdevice" dev_alloc_name is
@@ -79,6 +81,52 @@ static inline int __must_check kstrtos32_from_user(const char __user *s, size_t
return kstrtoint_from_user(s, count, base, res);
}
+/*
+ * This adds a nested function everywhere kfree_rcu() was called. This
+ * function frees the memory and is given as a function to call_rcu().
+ * The rcu callback could happen every time also after the module was
+ * unloaded and this will cause problems.
+ */
+#define kfree_rcu(data, rcuhead) do { \
+ void __kfree_rcu_fn(struct rcu_head *rcu_head) \
+ { \
+ void *___ptr; \
+ ___ptr = container_of(rcu_head, typeof(*(data)), rcuhead);\
+ kfree(___ptr); \
+ } \
+ call_rcu(&(data)->rcuhead, __kfree_rcu_fn); \
+ } while (0)
+
+#ifdef MODULE
+
+/*
+ * The define overwriting module_exit is based on the original module_exit
+ * which looks like this:
+ * #define module_exit(exitfn) \
+ * static inline exitcall_t __exittest(void) \
+ * { return exitfn; } \
+ * void cleanup_module(void) __attribute__((alias(#exitfn)));
+ *
+ * We replaced the call to the actual function exitfn() with a call to our
+ * function which calls the original exitfn() and then rcu_barrier()
+ *
+ * As a module will not be unloaded that ofter it should not have a big
+ * performance impact when rcu_barrier() is called on every module exit,
+ * also when no kfree_rcu() backport is used in that module.
+ */
+#undef module_exit
+#define module_exit(exitfn) \
+ static inline exitcall_t __exittest(void) \
+ { return exitfn; } \
+ void __exit __exit_compat(void) \
+ { \
+ exitfn(); \
+ rcu_barrier(); \
+ } \
+ void cleanup_module(void) __attribute__((alias("__exit_compat")));
+
+#endif
+
#endif /* (LINUX_VERSION_CODE < KERNEL_VERSION(3,0,0)) */
#endif /* LINUX_3_0_COMPAT_H */
--
1.7.4.1
This adds a nested function everywhere kfree_rcu() was called. This
function frees the memory and is given as a function to call_rcu().
The kfree_rcu define was made by Johannes Berg.
The rcu callback could happen every time also after the module was
unloaded and this will cause problems.
A rcu_barrier() was added into every module_exit so that this will not
be called after the module was unloaded.
The define overwriting module_exit is based on the original module_exit
which looks like this:
/* This is only required if you want to be unloadable. */
/#define module_exit(exitfn) \
static inline exitcall_t __exittest(void) \
{ return exitfn; } \
void cleanup_module(void) __attribute__((alias(#exitfn)));
We replaced the call to the actual function exitfn() with a call to our
function which calls the original exitfn() and then rcu_barrier()
As a module will not be unloaded that ofter it should not have a big
performance impact when rcu_barrier() is called on every module exit,
also when no kfree_rcu() backport is used in that module.
Signed-off-by: Hauke Mehrtens <[email protected]>
CC: Johannes Berg <[email protected]>
---
v2: remove compile check for exitfn
make function static
include/linux/compat-3.0.h | 46 ++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 46 insertions(+), 0 deletions(-)
diff --git a/include/linux/compat-3.0.h b/include/linux/compat-3.0.h
index 8c8720e..22ab539 100644
--- a/include/linux/compat-3.0.h
+++ b/include/linux/compat-3.0.h
@@ -5,6 +5,8 @@
#if (LINUX_VERSION_CODE < KERNEL_VERSION(3,0,0))
+#include <linux/rcupdate.h>
+
/*
* since commit 1c5cae815d19ffe02bdfda1260949ef2b1806171
* "net: call dev_alloc_name from register_netdevice" dev_alloc_name is
@@ -79,6 +81,50 @@ static inline int __must_check kstrtos32_from_user(const char __user *s, size_t
return kstrtoint_from_user(s, count, base, res);
}
+/*
+ * This adds a nested function everywhere kfree_rcu() was called. This
+ * function frees the memory and is given as a function to call_rcu().
+ * The rcu callback could happen every time also after the module was
+ * unloaded and this will cause problems.
+ */
+#define kfree_rcu(data, rcuhead) do { \
+ void __kfree_rcu_fn(struct rcu_head *rcu_head) \
+ { \
+ void *___ptr; \
+ ___ptr = container_of(rcu_head, typeof(*(data)), rcuhead);\
+ kfree(___ptr); \
+ } \
+ call_rcu(&(data)->rcuhead, __kfree_rcu_fn); \
+ } while (0)
+
+#ifdef MODULE
+
+/*
+ * The define overwriting module_exit is based on the original module_exit
+ * which looks like this:
+ * #define module_exit(exitfn) \
+ * static inline exitcall_t __exittest(void) \
+ * { return exitfn; } \
+ * void cleanup_module(void) __attribute__((alias(#exitfn)));
+ *
+ * We replaced the call to the actual function exitfn() with a call to our
+ * function which calls the original exitfn() and then rcu_barrier()
+ *
+ * As a module will not be unloaded that ofter it should not have a big
+ * performance impact when rcu_barrier() is called on every module exit,
+ * also when no kfree_rcu() backport is used in that module.
+ */
+#undef module_exit
+#define module_exit(exitfn) \
+ static void __exit __exit_compat(void) \
+ { \
+ exitfn(); \
+ rcu_barrier(); \
+ } \
+ void cleanup_module(void) __attribute__((alias("__exit_compat")));
+
+#endif
+
#endif /* (LINUX_VERSION_CODE < KERNEL_VERSION(3,0,0)) */
#endif /* LINUX_3_0_COMPAT_H */
--
1.7.4.1