Merge branch 'perf/fast' into perf/core
[linux-2.6-block.git] / include / linux / jump_label.h
CommitLineData
bf5438fc
JB
1#ifndef _LINUX_JUMP_LABEL_H
2#define _LINUX_JUMP_LABEL_H
3
d430d3d7
JB
4#include <linux/types.h>
5#include <linux/compiler.h>
b2029520 6#include <linux/workqueue.h>
d430d3d7 7
45f81b1c 8#if defined(CC_HAVE_ASM_GOTO) && defined(CONFIG_JUMP_LABEL)
d430d3d7
JB
9
10struct jump_label_key {
11 atomic_t enabled;
12 struct jump_entry *entries;
13#ifdef CONFIG_MODULES
14 struct jump_label_mod *next;
15#endif
16};
17
b2029520
GN
18struct jump_label_key_deferred {
19 struct jump_label_key key;
20 unsigned long timeout;
21 struct delayed_work work;
22};
23
bf5438fc
JB
24# include <asm/jump_label.h>
25# define HAVE_JUMP_LABEL
97ce2c88 26#endif /* CC_HAVE_ASM_GOTO && CONFIG_JUMP_LABEL */
bf5438fc
JB
27
28enum jump_label_type {
d430d3d7 29 JUMP_LABEL_DISABLE = 0,
bf5438fc 30 JUMP_LABEL_ENABLE,
bf5438fc
JB
31};
32
33struct module;
34
35#ifdef HAVE_JUMP_LABEL
36
d430d3d7 37#ifdef CONFIG_MODULES
d5d9a3b1 38#define JUMP_LABEL_INIT {ATOMIC_INIT(0), NULL, NULL}
d430d3d7 39#else
d5d9a3b1 40#define JUMP_LABEL_INIT {ATOMIC_INIT(0), NULL}
d430d3d7
JB
41#endif
42
43static __always_inline bool static_branch(struct jump_label_key *key)
44{
45 return arch_static_branch(key);
46}
47
bf5438fc
JB
48extern struct jump_entry __start___jump_table[];
49extern struct jump_entry __stop___jump_table[];
50
97ce2c88 51extern void jump_label_init(void);
91bad2f8
JB
52extern void jump_label_lock(void);
53extern void jump_label_unlock(void);
bf5438fc 54extern void arch_jump_label_transform(struct jump_entry *entry,
37348804 55 enum jump_label_type type);
20284aa7
JF
56extern void arch_jump_label_transform_static(struct jump_entry *entry,
57 enum jump_label_type type);
4c3ef6d7 58extern int jump_label_text_reserved(void *start, void *end);
d430d3d7
JB
59extern void jump_label_inc(struct jump_label_key *key);
60extern void jump_label_dec(struct jump_label_key *key);
b2029520 61extern void jump_label_dec_deferred(struct jump_label_key_deferred *key);
d430d3d7
JB
62extern bool jump_label_enabled(struct jump_label_key *key);
63extern void jump_label_apply_nops(struct module *mod);
b2029520
GN
64extern void jump_label_rate_limit(struct jump_label_key_deferred *key,
65 unsigned long rl);
bf5438fc 66
97ce2c88 67#else /* !HAVE_JUMP_LABEL */
bf5438fc 68
60063497 69#include <linux/atomic.h>
bf5438fc 70
d430d3d7 71#define JUMP_LABEL_INIT {ATOMIC_INIT(0)}
bf5438fc 72
d430d3d7
JB
73struct jump_label_key {
74 atomic_t enabled;
75};
bf5438fc 76
97ce2c88
JF
77static __always_inline void jump_label_init(void)
78{
79}
80
b2029520
GN
81struct jump_label_key_deferred {
82 struct jump_label_key key;
83};
84
d430d3d7
JB
85static __always_inline bool static_branch(struct jump_label_key *key)
86{
87 if (unlikely(atomic_read(&key->enabled)))
88 return true;
89 return false;
90}
bf5438fc 91
d430d3d7
JB
92static inline void jump_label_inc(struct jump_label_key *key)
93{
94 atomic_inc(&key->enabled);
95}
bf5438fc 96
d430d3d7 97static inline void jump_label_dec(struct jump_label_key *key)
bf5438fc 98{
d430d3d7 99 atomic_dec(&key->enabled);
bf5438fc
JB
100}
101
b2029520
GN
102static inline void jump_label_dec_deferred(struct jump_label_key_deferred *key)
103{
104 jump_label_dec(&key->key);
105}
106
4c3ef6d7
JB
107static inline int jump_label_text_reserved(void *start, void *end)
108{
109 return 0;
110}
111
91bad2f8
JB
112static inline void jump_label_lock(void) {}
113static inline void jump_label_unlock(void) {}
114
d430d3d7
JB
115static inline bool jump_label_enabled(struct jump_label_key *key)
116{
117 return !!atomic_read(&key->enabled);
118}
bf5438fc 119
d430d3d7
JB
120static inline int jump_label_apply_nops(struct module *mod)
121{
122 return 0;
123}
b2029520
GN
124
125static inline void jump_label_rate_limit(struct jump_label_key_deferred *key,
126 unsigned long rl)
127{
128}
97ce2c88 129#endif /* HAVE_JUMP_LABEL */
d430d3d7 130
ac99b862
PZ
131#define jump_label_key_enabled ((struct jump_label_key){ .enabled = ATOMIC_INIT(1), })
132#define jump_label_key_disabled ((struct jump_label_key){ .enabled = ATOMIC_INIT(0), })
133
97ce2c88 134#endif /* _LINUX_JUMP_LABEL_H */