Skip to content

Commit db1388b

Browse files
tzanussirostedt
authored andcommitted
tracing: Add support for named triggers
Named triggers are sets of triggers that share a common set of trigger data. An example of functionality that could benefit from this type of capability would be a set of inlined probes that would each contribute event counts, for example, to a shared counter data structure. The first named trigger registered with a given name owns the common trigger data that the others subsequently registered with the same name will reference. The functions defined here allow users to add, delete, and find named triggers. It also adds functions to pause and unpause named triggers; since named triggers act upon common data, they should also be paused and unpaused as a group. Link: http://lkml.kernel.org/r/c09ff648360f65b10a3e321eddafe18060b4a04f.1457029949.git.tom.zanussi@linux.intel.com Signed-off-by: Tom Zanussi <[email protected]> Tested-by: Masami Hiramatsu <[email protected]> Reviewed-by: Namhyung Kim <[email protected]> Signed-off-by: Steven Rostedt <[email protected]>
1 parent 52a7f16 commit db1388b

File tree

2 files changed

+156
-0
lines changed

2 files changed

+156
-0
lines changed

kernel/trace/trace.h

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1184,7 +1184,11 @@ struct event_trigger_data {
11841184
char *filter_str;
11851185
void *private_data;
11861186
bool paused;
1187+
bool paused_tmp;
11871188
struct list_head list;
1189+
char *name;
1190+
struct list_head named_list;
1191+
struct event_trigger_data *named_data;
11881192
};
11891193

11901194
/* Avoid typos */
@@ -1227,6 +1231,15 @@ extern void unregister_trigger(char *glob, struct event_trigger_ops *ops,
12271231
extern int set_trigger_filter(char *filter_str,
12281232
struct event_trigger_data *trigger_data,
12291233
struct trace_event_file *file);
1234+
extern struct event_trigger_data *find_named_trigger(const char *name);
1235+
extern bool is_named_trigger(struct event_trigger_data *test);
1236+
extern int save_named_trigger(const char *name,
1237+
struct event_trigger_data *data);
1238+
extern void del_named_trigger(struct event_trigger_data *data);
1239+
extern void pause_named_trigger(struct event_trigger_data *data);
1240+
extern void unpause_named_trigger(struct event_trigger_data *data);
1241+
extern void set_named_trigger_data(struct event_trigger_data *data,
1242+
struct event_trigger_data *named_data);
12301243
extern int register_event_command(struct event_command *cmd);
12311244
extern int unregister_event_command(struct event_command *cmd);
12321245
extern int register_trigger_hist_enable_disable_cmds(void);

kernel/trace/trace_events_trigger.c

Lines changed: 143 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -641,6 +641,7 @@ event_trigger_callback(struct event_command *cmd_ops,
641641
trigger_data->ops = trigger_ops;
642642
trigger_data->cmd_ops = cmd_ops;
643643
INIT_LIST_HEAD(&trigger_data->list);
644+
INIT_LIST_HEAD(&trigger_data->named_list);
644645

645646
if (glob[0] == '!') {
646647
cmd_ops->unreg(glob+1, trigger_ops, trigger_data, file);
@@ -764,6 +765,148 @@ int set_trigger_filter(char *filter_str,
764765
return ret;
765766
}
766767

768+
static LIST_HEAD(named_triggers);
769+
770+
/**
771+
* find_named_trigger - Find the common named trigger associated with @name
772+
* @name: The name of the set of named triggers to find the common data for
773+
*
774+
* Named triggers are sets of triggers that share a common set of
775+
* trigger data. The first named trigger registered with a given name
776+
* owns the common trigger data that the others subsequently
777+
* registered with the same name will reference. This function
778+
* returns the common trigger data associated with that first
779+
* registered instance.
780+
*
781+
* Return: the common trigger data for the given named trigger on
782+
* success, NULL otherwise.
783+
*/
784+
struct event_trigger_data *find_named_trigger(const char *name)
785+
{
786+
struct event_trigger_data *data;
787+
788+
if (!name)
789+
return NULL;
790+
791+
list_for_each_entry(data, &named_triggers, named_list) {
792+
if (data->named_data)
793+
continue;
794+
if (strcmp(data->name, name) == 0)
795+
return data;
796+
}
797+
798+
return NULL;
799+
}
800+
801+
/**
802+
* is_named_trigger - determine if a given trigger is a named trigger
803+
* @test: The trigger data to test
804+
*
805+
* Return: true if 'test' is a named trigger, false otherwise.
806+
*/
807+
bool is_named_trigger(struct event_trigger_data *test)
808+
{
809+
struct event_trigger_data *data;
810+
811+
list_for_each_entry(data, &named_triggers, named_list) {
812+
if (test == data)
813+
return true;
814+
}
815+
816+
return false;
817+
}
818+
819+
/**
820+
* save_named_trigger - save the trigger in the named trigger list
821+
* @name: The name of the named trigger set
822+
* @data: The trigger data to save
823+
*
824+
* Return: 0 if successful, negative error otherwise.
825+
*/
826+
int save_named_trigger(const char *name, struct event_trigger_data *data)
827+
{
828+
data->name = kstrdup(name, GFP_KERNEL);
829+
if (!data->name)
830+
return -ENOMEM;
831+
832+
list_add(&data->named_list, &named_triggers);
833+
834+
return 0;
835+
}
836+
837+
/**
838+
* del_named_trigger - delete a trigger from the named trigger list
839+
* @data: The trigger data to delete
840+
*/
841+
void del_named_trigger(struct event_trigger_data *data)
842+
{
843+
kfree(data->name);
844+
data->name = NULL;
845+
846+
list_del(&data->named_list);
847+
}
848+
849+
static void __pause_named_trigger(struct event_trigger_data *data, bool pause)
850+
{
851+
struct event_trigger_data *test;
852+
853+
list_for_each_entry(test, &named_triggers, named_list) {
854+
if (strcmp(test->name, data->name) == 0) {
855+
if (pause) {
856+
test->paused_tmp = test->paused;
857+
test->paused = true;
858+
} else {
859+
test->paused = test->paused_tmp;
860+
}
861+
}
862+
}
863+
}
864+
865+
/**
866+
* pause_named_trigger - Pause all named triggers with the same name
867+
* @data: The trigger data of a named trigger to pause
868+
*
869+
* Pauses a named trigger along with all other triggers having the
870+
* same name. Because named triggers share a common set of data,
871+
* pausing only one is meaningless, so pausing one named trigger needs
872+
* to pause all triggers with the same name.
873+
*/
874+
void pause_named_trigger(struct event_trigger_data *data)
875+
{
876+
__pause_named_trigger(data, true);
877+
}
878+
879+
/**
880+
* unpause_named_trigger - Un-pause all named triggers with the same name
881+
* @data: The trigger data of a named trigger to unpause
882+
*
883+
* Un-pauses a named trigger along with all other triggers having the
884+
* same name. Because named triggers share a common set of data,
885+
* unpausing only one is meaningless, so unpausing one named trigger
886+
* needs to unpause all triggers with the same name.
887+
*/
888+
void unpause_named_trigger(struct event_trigger_data *data)
889+
{
890+
__pause_named_trigger(data, false);
891+
}
892+
893+
/**
894+
* set_named_trigger_data - Associate common named trigger data
895+
* @data: The trigger data of a named trigger to unpause
896+
*
897+
* Named triggers are sets of triggers that share a common set of
898+
* trigger data. The first named trigger registered with a given name
899+
* owns the common trigger data that the others subsequently
900+
* registered with the same name will reference. This function
901+
* associates the common trigger data from the first trigger with the
902+
* given trigger.
903+
*/
904+
void set_named_trigger_data(struct event_trigger_data *data,
905+
struct event_trigger_data *named_data)
906+
{
907+
data->named_data = named_data;
908+
}
909+
767910
static void
768911
traceon_trigger(struct event_trigger_data *data, void *rec)
769912
{

0 commit comments

Comments
 (0)