162306a36Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-only */
262306a36Sopenharmony_ci/*
362306a36Sopenharmony_ci * thread-stack.h: Synthesize a thread's stack using call / return events
462306a36Sopenharmony_ci * Copyright (c) 2014, Intel Corporation.
562306a36Sopenharmony_ci */
662306a36Sopenharmony_ci
762306a36Sopenharmony_ci#ifndef __PERF_THREAD_STACK_H
862306a36Sopenharmony_ci#define __PERF_THREAD_STACK_H
962306a36Sopenharmony_ci
1062306a36Sopenharmony_ci#include <sys/types.h>
1162306a36Sopenharmony_ci
1262306a36Sopenharmony_ci#include <linux/types.h>
1362306a36Sopenharmony_ci
1462306a36Sopenharmony_cistruct thread;
1562306a36Sopenharmony_cistruct comm;
1662306a36Sopenharmony_cistruct ip_callchain;
1762306a36Sopenharmony_cistruct symbol;
1862306a36Sopenharmony_cistruct dso;
1962306a36Sopenharmony_cistruct perf_sample;
2062306a36Sopenharmony_cistruct addr_location;
2162306a36Sopenharmony_cistruct call_path;
2262306a36Sopenharmony_ci
2362306a36Sopenharmony_ci/*
2462306a36Sopenharmony_ci * Call/Return flags.
2562306a36Sopenharmony_ci *
2662306a36Sopenharmony_ci * CALL_RETURN_NO_CALL: 'return' but no matching 'call'
2762306a36Sopenharmony_ci * CALL_RETURN_NO_RETURN: 'call' but no matching 'return'
2862306a36Sopenharmony_ci * CALL_RETURN_NON_CALL: a branch but not a 'call' to the start of a different
2962306a36Sopenharmony_ci *                       symbol
3062306a36Sopenharmony_ci */
3162306a36Sopenharmony_cienum {
3262306a36Sopenharmony_ci	CALL_RETURN_NO_CALL	= 1 << 0,
3362306a36Sopenharmony_ci	CALL_RETURN_NO_RETURN	= 1 << 1,
3462306a36Sopenharmony_ci	CALL_RETURN_NON_CALL	= 1 << 2,
3562306a36Sopenharmony_ci};
3662306a36Sopenharmony_ci
3762306a36Sopenharmony_ci/**
3862306a36Sopenharmony_ci * struct call_return - paired call/return information.
3962306a36Sopenharmony_ci * @thread: thread in which call/return occurred
4062306a36Sopenharmony_ci * @comm: comm in which call/return occurred
4162306a36Sopenharmony_ci * @cp: call path
4262306a36Sopenharmony_ci * @call_time: timestamp of call (if known)
4362306a36Sopenharmony_ci * @return_time: timestamp of return (if known)
4462306a36Sopenharmony_ci * @branch_count: number of branches seen between call and return
4562306a36Sopenharmony_ci * @insn_count: approx. number of instructions between call and return
4662306a36Sopenharmony_ci * @cyc_count: approx. number of cycles between call and return
4762306a36Sopenharmony_ci * @call_ref: external reference to 'call' sample (e.g. db_id)
4862306a36Sopenharmony_ci * @return_ref:  external reference to 'return' sample (e.g. db_id)
4962306a36Sopenharmony_ci * @db_id: id used for db-export
5062306a36Sopenharmony_ci * @parent_db_id: id of parent call used for db-export
5162306a36Sopenharmony_ci * @flags: Call/Return flags
5262306a36Sopenharmony_ci */
5362306a36Sopenharmony_cistruct call_return {
5462306a36Sopenharmony_ci	struct thread *thread;
5562306a36Sopenharmony_ci	struct comm *comm;
5662306a36Sopenharmony_ci	struct call_path *cp;
5762306a36Sopenharmony_ci	u64 call_time;
5862306a36Sopenharmony_ci	u64 return_time;
5962306a36Sopenharmony_ci	u64 branch_count;
6062306a36Sopenharmony_ci	u64 insn_count;
6162306a36Sopenharmony_ci	u64 cyc_count;
6262306a36Sopenharmony_ci	u64 call_ref;
6362306a36Sopenharmony_ci	u64 return_ref;
6462306a36Sopenharmony_ci	u64 db_id;
6562306a36Sopenharmony_ci	u64 parent_db_id;
6662306a36Sopenharmony_ci	u32 flags;
6762306a36Sopenharmony_ci};
6862306a36Sopenharmony_ci
6962306a36Sopenharmony_ci/**
7062306a36Sopenharmony_ci * struct call_return_processor - provides a call-back to consume call-return
7162306a36Sopenharmony_ci *                                information.
7262306a36Sopenharmony_ci * @cpr: call path root
7362306a36Sopenharmony_ci * @process: call-back that accepts call/return information
7462306a36Sopenharmony_ci * @data: anonymous data for call-back
7562306a36Sopenharmony_ci */
7662306a36Sopenharmony_cistruct call_return_processor {
7762306a36Sopenharmony_ci	struct call_path_root *cpr;
7862306a36Sopenharmony_ci	int (*process)(struct call_return *cr, u64 *parent_db_id, void *data);
7962306a36Sopenharmony_ci	void *data;
8062306a36Sopenharmony_ci};
8162306a36Sopenharmony_ci
8262306a36Sopenharmony_ciint thread_stack__event(struct thread *thread, int cpu, u32 flags, u64 from_ip,
8362306a36Sopenharmony_ci			u64 to_ip, u16 insn_len, u64 trace_nr, bool callstack,
8462306a36Sopenharmony_ci			unsigned int br_stack_sz, bool mispred_all);
8562306a36Sopenharmony_civoid thread_stack__set_trace_nr(struct thread *thread, int cpu, u64 trace_nr);
8662306a36Sopenharmony_civoid thread_stack__sample(struct thread *thread, int cpu, struct ip_callchain *chain,
8762306a36Sopenharmony_ci			  size_t sz, u64 ip, u64 kernel_start);
8862306a36Sopenharmony_civoid thread_stack__sample_late(struct thread *thread, int cpu,
8962306a36Sopenharmony_ci			       struct ip_callchain *chain, size_t sz, u64 ip,
9062306a36Sopenharmony_ci			       u64 kernel_start);
9162306a36Sopenharmony_civoid thread_stack__br_sample(struct thread *thread, int cpu,
9262306a36Sopenharmony_ci			     struct branch_stack *dst, unsigned int sz);
9362306a36Sopenharmony_civoid thread_stack__br_sample_late(struct thread *thread, int cpu,
9462306a36Sopenharmony_ci				  struct branch_stack *dst, unsigned int sz,
9562306a36Sopenharmony_ci				  u64 sample_ip, u64 kernel_start);
9662306a36Sopenharmony_ciint thread_stack__flush(struct thread *thread);
9762306a36Sopenharmony_civoid thread_stack__free(struct thread *thread);
9862306a36Sopenharmony_cisize_t thread_stack__depth(struct thread *thread, int cpu);
9962306a36Sopenharmony_ci
10062306a36Sopenharmony_cistruct call_return_processor *
10162306a36Sopenharmony_cicall_return_processor__new(int (*process)(struct call_return *cr, u64 *parent_db_id, void *data),
10262306a36Sopenharmony_ci			   void *data);
10362306a36Sopenharmony_civoid call_return_processor__free(struct call_return_processor *crp);
10462306a36Sopenharmony_ciint thread_stack__process(struct thread *thread, struct comm *comm,
10562306a36Sopenharmony_ci			  struct perf_sample *sample,
10662306a36Sopenharmony_ci			  struct addr_location *from_al,
10762306a36Sopenharmony_ci			  struct addr_location *to_al, u64 ref,
10862306a36Sopenharmony_ci			  struct call_return_processor *crp);
10962306a36Sopenharmony_ci
11062306a36Sopenharmony_ci#endif
111