aboutsummaryrefslogtreecommitdiffstats
path: root/system_cmds/lsmp.tproj/common.h
blob: 9a47012d07212998517aa0fa1125bc4a724397dd (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
/*
 * Copyright (c) 2002-2016 Apple Inc. All rights reserved.
 *
 * @APPLE_LICENSE_HEADER_START@
 *
 * The contents of this file constitute Original Code as defined in and
 * are subject to the Apple Public Source License Version 1.1 (the
 * "License").  You may not use this file except in compliance with the
 * License.  Please obtain a copy of the License at
 * http://www.apple.com/publicsource and read it before using this file.
 *
 * This Original Code and all software distributed under the License are
 * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the
 * License for the specific language governing rights and limitations
 * under the License.
 *
 * @APPLE_LICENSE_HEADER_END@
 */


#ifndef system_cmds_common_h
#define system_cmds_common_h

#include <mach/mach.h>
#include "json.h"

#define PROC_NAME_LEN 100
#define BUFSTR_LEN 30
#define VOUCHER_DETAIL_MAXLEN 1024

/* common struct to hold all configurations, static and args based */
struct prog_configs {
    boolean_t show_all_tasks;
    boolean_t show_voucher_details;
    boolean_t verbose;
    int       voucher_detail_length;
    pid_t     pid; /* if user focusing only one pid */
    JSON_t    json_output;
};

extern struct prog_configs lsmp_config;

/* exception port information */
struct exc_port_info {
    mach_msg_type_number_t   count;
    mach_port_t      ports[EXC_TYPES_COUNT];
    exception_mask_t masks[EXC_TYPES_COUNT];
    exception_behavior_t behaviors[EXC_TYPES_COUNT];
    thread_state_flavor_t flavors[EXC_TYPES_COUNT];
};

/* private structure to hold thread specific information */
struct my_per_thread_info {
    mach_port_t thread;
    uint32_t th_kobject;
    uint64_t th_id;
    char * voucher_detail;
};

/* kobject to name hash table declarations */
#define K2N_TABLE_SIZE	256

struct k2n_table_node {
    natural_t kobject; /* kobject referred to by the name -- the key into the table */
    ipc_info_name_t *info_name; /* info about the name that refers to the key kobject -- value of the table */
    struct k2n_table_node *next;
};

struct k2n_table_node *k2n_table_lookup_next(struct k2n_table_node *node, natural_t kobject);
struct k2n_table_node *k2n_table_lookup(struct k2n_table_node **table, natural_t kobject);

/* private structure to wrap up per-task info */
typedef struct my_per_task_info {
    task_t task;
    pid_t pid;
    vm_address_t task_kobject;
    ipc_info_space_t info;
    ipc_info_name_array_t table;
    mach_msg_type_number_t tableCount;
    ipc_info_tree_name_array_t tree;
    mach_msg_type_number_t treeCount;
    boolean_t valid; /* TRUE if all data is accurately collected */
    struct k2n_table_node *k2ntable[K2N_TABLE_SIZE];
    char processName[PROC_NAME_LEN];
    struct exc_port_info exceptionInfo;
    struct my_per_thread_info * threadInfos; /* dynamically allocated in collect_per_task_info */
    unsigned int threadCount;
    struct exc_port_info *threadExceptionInfos;  /* this is 2 dimensional array with threadCount X struct exc_port_info  of ports */
} my_per_task_info_t;


/*
 * WARNING - these types are copied from xnu/osfmk/kern/ipc_kobject.h
 * Need to stay in sync to print accurate results.
 */
#define IKOT_NONE                  0
#define IKOT_THREAD_CONTROL        1
#define IKOT_TASK_CONTROL          2
#define IKOT_HOST                  3
#define IKOT_HOST_PRIV             4
#define IKOT_PROCESSOR             5
#define IKOT_PSET                  6
#define IKOT_PSET_NAME             7
#define IKOT_TIMER                 8
#define IKOT_PAGING_REQUEST        9
#define IKOT_MIG                  10
#define IKOT_MEMORY_OBJECT        11
#define IKOT_XMM_PAGER            12
#define IKOT_XMM_KERNEL           13
#define IKOT_XMM_REPLY            14
#define IKOT_UND_REPLY            15
#define IKOT_HOST_NOTIFY          16
#define IKOT_HOST_SECURITY        17
#define IKOT_LEDGER               18
#define IKOT_MASTER_DEVICE        19
#define IKOT_TASK_NAME            20
#define IKOT_SUBSYSTEM            21
#define IKOT_IO_DONE_QUEUE        22
#define IKOT_SEMAPHORE            23
#define IKOT_LOCK_SET             24
#define IKOT_CLOCK                25
#define IKOT_CLOCK_CTRL           26
#define IKOT_IOKIT_IDENT          27
#define IKOT_NAMED_ENTRY          28
#define IKOT_IOKIT_CONNECT        29
#define IKOT_IOKIT_OBJECT         30
#define IKOT_UPL                  31
#define IKOT_MEM_OBJ_CONTROL      32
#define IKOT_AU_SESSIONPORT       33
#define IKOT_FILEPORT             34
#define IKOT_LABELH               35
#define IKOT_TASK_RESUME          36
#define IKOT_VOUCHER              37
#define IKOT_VOUCHER_ATTR_CONTROL 38
#define IKOT_WORK_INTERVAL        39
#define IKOT_UX_HANDLER           40
#define IKOT_UEXT_OBJECT          41
#define IKOT_ARCADE_REG           42
#define IKOT_EVENTLINK            43
#define IKOT_TASK_INSPECT         44
#define IKOT_TASK_READ            45
#define IKOT_THREAD_INSPECT       46
#define IKOT_THREAD_READ          47
#define IKOT_SUID_CRED            48
#define IKOT_HYPERVISOR           49

#define IKOT_UNKNOWN              50	/* magic catchall	*/
#define IKOT_MAX_TYPE             (IKOT_UNKNOWN+1)	/* # of IKOT_ types	*/


#define PORT_FLAG_TO_INDEX(flag) ( __builtin_ctz(flag) ) /* count trailing zeros */
#define INDEX_TO_PORT_FLAG(idx) ( 1 << idx )
typedef struct port_status_flag_info {
    natural_t flag; /* MACH_PORT_STATUS_FLAG_* */
    const char *compact_name; /* Single character name for compact representation */
    const char *name; /* human readable long name */
} port_status_flag_info_t;

/*
 * list of names for possible MACH_PORT_STATUS_FLAG_*
 * indexed by PORT_FLAG_TO_INDEX(MACH_PORT_STATUS_FLAG_*)
 */
extern const port_status_flag_info_t port_status_flags[];

#define _SHOW_PORT_STATUS_FLAG(flags, flag) \
  (flags & flag) ? port_status_flags[PORT_FLAG_TO_INDEX(flag)].compact_name : "-"
#define SHOW_PORT_STATUS_FLAGS(flags) \
  _SHOW_PORT_STATUS_FLAG(flags, MACH_PORT_STATUS_FLAG_TEMPOWNER), \
  _SHOW_PORT_STATUS_FLAG(flags, MACH_PORT_STATUS_FLAG_GUARDED), \
  _SHOW_PORT_STATUS_FLAG(flags, MACH_PORT_STATUS_FLAG_STRICT_GUARD), \
  _SHOW_PORT_STATUS_FLAG(flags, MACH_PORT_STATUS_FLAG_IMP_DONATION), \
  _SHOW_PORT_STATUS_FLAG(flags, MACH_PORT_STATUS_FLAG_REVIVE), \
  _SHOW_PORT_STATUS_FLAG(flags, MACH_PORT_STATUS_FLAG_TASKPTR)


uint32_t show_recipe_detail(mach_voucher_attr_recipe_t recipe, char * voucher_outstr, uint32_t maxlen, JSON_t json);
char *copy_voucher_detail(mach_port_t task, mach_port_name_t voucher, JSON_t json);

/* mach port related functions */
const char * kobject_name(natural_t kotype);
void get_receive_port_context(task_t taskp, mach_port_name_t portname, mach_port_context_t *context);
int get_recieve_port_status(task_t taskp, mach_port_name_t portname, mach_port_info_ext_t *info);
void show_task_mach_ports(my_per_task_info_t *taskinfo, uint32_t taskCount, my_per_task_info_t *allTaskInfos, JSON_t json);

/* task and thread related helper functions */
kern_return_t collect_per_task_info(my_per_task_info_t *taskinfo, task_t target_task);
my_per_task_info_t * allocate_taskinfo_memory(uint32_t taskCount);
void deallocate_taskinfo_memory(my_per_task_info_t *data);
kern_return_t print_task_exception_info(my_per_task_info_t *taskinfo, JSON_t json);
kern_return_t print_task_threads_special_ports(my_per_task_info_t *taskinfo, JSON_t json);
my_per_task_info_t * get_taskinfo_by_kobject(natural_t kobj);

void get_exc_behavior_string(exception_behavior_t b, char *out_string, size_t len);
void get_exc_mask_string(exception_mask_t m, char *out_string, size_t len);
kern_return_t get_taskinfo_of_receiver_by_send_right(ipc_info_name_t *sendright, my_per_task_info_t **out_taskinfo, mach_port_name_t *out_recv_info);
kern_return_t get_ipc_info_from_lsmp_spaceinfo(mach_port_t port_name, ipc_info_name_t *out_sendright);

/* basic util functions */
uint32_t print_hex_data(char *outstr, uint32_t maxlen, char *prefix, char *desc, void *addr, int len);

#endif