xref: /PHP-7.3/.gdbinit (revision 3362620b)
1define set_ts
2	set $tsrm_ls = $arg0
3end
4
5document set_ts
6	set the ts resource, it is impossible for gdb to
7	call ts_resource_ex while no process is running,
8	but we could get the resource from the argument
9	of frame info.
10end
11
12define ____executor_globals
13	if basic_functions_module.zts
14		if !$tsrm_ls
15			set $tsrm_ls = ts_resource_ex(0, 0)
16		end
17		set $eg = ((zend_executor_globals*) (*((void ***) $tsrm_ls))[executor_globals_id-1])
18		set $cg = ((zend_compiler_globals*) (*((void ***) $tsrm_ls))[compiler_globals_id-1])
19		set $eg_ptr = $eg
20	else
21		set $eg = executor_globals
22		set $cg = compiler_globals
23		set $eg_ptr = (zend_executor_globals*) &executor_globals
24	end
25end
26
27document ____executor_globals
28	portable way of accessing executor_globals, set $eg
29	this also sets compiler_globals to $cg
30	ZTS detection is automatically based on ext/standard module struct
31end
32
33define print_cvs
34	if $argc == 0
35		____executor_globals
36		set $cv_ex_ptr = $eg.current_execute_data
37	else
38		set $cv_ex_ptr = (zend_execute_data *)$arg0
39	end
40	set $cv_count = $cv_ex_ptr.func.op_array.last_var
41	set $cv = $cv_ex_ptr.func.op_array.vars
42	set $cv_idx = 0
43	set $callFrameSize = (sizeof(zend_execute_data) + sizeof(zval) - 1) / sizeof(zval)
44
45	printf "Compiled variables count: %d\n\n", $cv_count
46	while $cv_idx < $cv_count
47		printf "[%d] '%s'\n", $cv_idx, $cv[$cv_idx].val
48		set $zvalue = ((zval *) $cv_ex_ptr) + $callFrameSize + $cv_idx
49		printzv $zvalue
50		set $cv_idx = $cv_idx + 1
51	end
52end
53
54document print_cvs
55	Prints the compiled variables and their values.
56	If a zend_execute_data pointer is set this will print the compiled
57	variables of that scope. If no parameter is used it will use
58	current_execute_data for scope.
59
60	usage: print_cvs [zend_execute_data *]
61end
62
63define dump_bt
64	set $ex = $arg0
65	while $ex
66		printf "[%p] ", $ex
67		set $func = $ex->func
68		if $func
69			if $ex->This->value.obj
70				if $func->common.scope
71					printf "%s->", $func->common.scope->name->val
72				else
73					printf "%s->", $ex->This->value.obj->ce.name->val
74				end
75			else
76				if $func->common.scope
77					printf "%s::", $func->common.scope->name->val
78				end
79			end
80
81			if $func->common.function_name
82				printf "%s(", $func->common.function_name->val
83			else
84				printf "(main"
85			end
86
87			set $callFrameSize = (sizeof(zend_execute_data) + sizeof(zval) - 1) / sizeof(zval)
88
89			set $count = $ex->This.u2.num_args
90			set $arg = 0
91			while $arg < $count
92				if $arg > 0
93					printf ", "
94				end
95
96				set $zvalue = (zval *) $ex + $callFrameSize + $arg
97				set $type = $zvalue->u1.v.type
98				if $type == 1
99					printf "NULL"
100				end
101				if $type == 2
102					printf "false"
103				end
104				if $type == 3
105					printf "true"
106				end
107				if $type == 4
108					printf "%ld", $zvalue->value.lval
109				end
110				if $type == 5
111					printf "%f", $zvalue->value.dval
112				end
113				if $type == 6
114					____print_str $zvalue->value.str->val $zvalue->value.str->len
115				end
116				if $type == 7
117					printf "array(%d)[%p]", $zvalue->value.arr->nNumOfElements, $zvalue
118				end
119				if $type == 8
120					printf "object[%p]", $zvalue
121				end
122				if $type == 9
123					printf "resource(#%d)", $zvalue->value.lval
124				end
125				if $type == 10
126					printf "reference"
127				end
128				if $type > 10
129					printf "unknown type %d", $type
130				end
131				set $arg = $arg + 1
132			end
133
134			printf ") "
135		else
136			printf "??? "
137		end
138		if $func != 0
139			if $func->type == 2
140				printf "%s:%d ", $func->op_array.filename->val, $ex->opline->lineno
141			else
142				printf "[internal function]"
143			end
144		end
145		set $ex = $ex->prev_execute_data
146		printf "\n"
147	end
148end
149
150document dump_bt
151	dumps the current execution stack. usage: dump_bt executor_globals.current_execute_data
152end
153
154define printzv
155	set $ind = 1
156	____printzv $arg0 0
157end
158
159document printzv
160	prints zval contents
161end
162
163define ____printzv_contents
164	set $zvalue = $arg0
165	set $type = $zvalue->u1.v.type
166
167	# 15 == IS_INDIRECT
168	if $type > 5 && $type != 15
169		printf "(refcount=%d) ", $zvalue->value.counted->gc.refcount
170	end
171
172	if $type == 0
173		printf "UNDEF"
174	end
175	if $type == 1
176		printf "NULL"
177	end
178	if $type == 2
179		printf "bool: false"
180	end
181	if $type == 3
182		printf "bool: true"
183	end
184	if $type == 4
185		printf "long: %ld", $zvalue->value.lval
186	end
187	if $type == 5
188		printf "double: %f", $zvalue->value.dval
189	end
190	if $type == 6
191		printf "string: %s", $zvalue->value.str->val
192	end
193	if $type == 7
194		printf "array: "
195		if ! $arg1
196			set $ind = $ind + 1
197			____print_ht $zvalue->value.arr 1
198			set $ind = $ind - 1
199			set $i = $ind
200			while $i > 0
201				printf "  "
202				set $i = $i - 1
203			end
204		end
205		set $type = 0
206	end
207	if $type == 8
208		printf "object"
209		____executor_globals
210		set $handle = $zvalue->value.obj.handle
211		set $handlers = $zvalue->value.obj.handlers
212		set $zobj = $zvalue->value.obj
213		set $cname = $zobj->ce->name->val
214		printf "(%s) #%d", $cname, $handle
215		if ! $arg1
216			if $handlers->get_properties == &zend_std_get_properties
217				if $zobj->properties
218					set $ht = $zobj->properties
219				else
220					set $ht = &$zobj->ce->properties_info
221				end
222				printf "\nProperties "
223				if $ht
224					set $ind = $ind + 1
225					____print_ht $ht 1
226					set $ind = $ind - 1
227					set $i = $ind
228					while $i > 0
229						printf "  "
230						set $i = $i - 1
231					end
232				else
233					echo "not found"
234				end
235			end
236		end
237		set $type = 0
238	end
239	if $type == 9
240		printf "resource: #%d", $zvalue->value.res->handle
241	end
242	if $type == 10
243		printf "reference: "
244		____printzv &$zvalue->value.ref->val $arg1
245	end
246	if $type == 11
247		printf "const: %s", $zvalue->value.str->val
248	end
249	if $type == 12
250		printf "CONSTANT_AST"
251	end
252	if $type == 13
253		printf "_BOOL"
254	end
255	if $type == 14
256		printf "CALLABLE"
257	end
258	if $type == 15
259		printf "indirect: "
260		____printzv $zvalue->value.zv $arg1
261	end
262	if $type == 17
263		printf "pointer: %p", $zvalue->value.ptr
264	end
265	if $type == 18
266		printf "ITERABLE"
267	end
268	if $type == 19
269		printf "VOID"
270	end
271	if $type == 20
272		printf "_ERROR"
273	end
274	if $type == 16 || $type > 20
275		printf "unknown type %d", $type
276	end
277	printf "\n"
278end
279
280define ____printzv
281	____executor_globals
282	set $zvalue = $arg0
283
284	printf "[%p] ", $zvalue
285
286	set $zcontents = (zval*) $zvalue
287	if $arg1
288		____printzv_contents $zcontents $arg1
289	else
290		____printzv_contents $zcontents 0
291	end
292end
293
294define print_global_vars
295	____executor_globals
296	set $symtable = ((HashTable *)&($eg_ptr->symbol_table))
297	print_ht $symtable
298end
299
300document print_global_vars
301	Prints the global variables
302end
303
304define print_const_table
305	set $ind = 1
306	printf "[%p] {\n", $arg0
307	____print_ht $arg0 4
308	printf "}\n"
309end
310
311document print_const_table
312	Dumps elements of Constants HashTable
313	Example: print_const_table executor_globals.zend_constants
314end
315
316define ____print_ht
317	set $ht = (HashTable*)$arg0
318	set $n = $ind
319	while $n > 0
320		printf "  "
321		set $n = $n - 1
322	end
323
324	if $ht->u.v.flags & 4
325		printf "Packed"
326	else
327		printf "Hash"
328	end
329	printf "(%d)[%p]: {\n", $ht->nNumOfElements, $ht
330
331	set $num = $ht->nNumUsed
332	set $i = 0
333	set $ind = $ind + 1
334	while $i < $num
335		set $p = (Bucket*)($ht->arData + $i)
336		set $n = $ind
337		if $p->val.u1.v.type > 0
338			while $n > 0
339				printf "  "
340				set $n = $n - 1
341			end
342			printf "[%d] ", $i
343			if $p->key
344				printf "%s => ", $p->key->val
345			else
346				printf "%d => ", $p->h
347			end
348			if $arg1 == 0
349				printf "%p\n", (zval *)&$p->val
350			end
351			if $arg1 == 1
352				set $zval = (zval *)&$p->val
353				____printzv $zval 1
354			end
355			if $arg1 == 2
356				printf "%s\n", (char*)$p->val.value.ptr
357			end
358			if $arg1 == 3
359				set $func = (zend_function*)$p->val.value.ptr
360				printf "\"%s\"\n", $func->common.function_name->val
361			end
362			if $arg1 == 4
363				set $const = (zend_constant *)$p->val.value.ptr
364				____printzv $const 1
365			end
366		end
367		set $i = $i + 1
368	end
369	set $ind = $ind - 1
370	printf "}\n"
371end
372
373define print_ht
374	set $ind = 0
375	____print_ht $arg0 1
376end
377
378document print_ht
379	dumps elements of HashTable made of zval
380end
381
382define print_htptr
383	set $ind = 0
384	____print_ht $arg0 0
385end
386
387document print_htptr
388	dumps elements of HashTable made of pointers
389end
390
391define print_htstr
392	set $ind = 0
393	____print_ht $arg0 2
394end
395
396document print_htstr
397	dumps elements of HashTable made of strings
398end
399
400define print_ft
401	set $ind = 0
402	____print_ht $arg0 3
403end
404
405document print_ft
406	dumps a function table (HashTable)
407end
408
409define ____print_inh_class
410	set $ce = $arg0
411	if $ce->ce_flags & 0x10 || $ce->ce_flags & 0x20
412		printf "abstract "
413	else
414		if $ce->ce_flags & 0x40
415			printf "final "
416		end
417	end
418	printf "class %s", $ce->name->val
419	if $ce->parent != 0
420		printf " extends %s", $ce->parent->name->val
421	end
422	if $ce->num_interfaces != 0
423		printf " implements"
424		set $tmp = 0
425		while $tmp < $ce->num_interfaces
426			printf " %s", $ce->interfaces[$tmp]->name->val
427			set $tmp = $tmp + 1
428			if $tmp < $ce->num_interfaces
429				printf ","
430			end
431		end
432	end
433	set $ce = $ce->parent
434end
435
436define ____print_inh_iface
437	set $ce = $arg0
438	printf "interface %s", $ce->name->val
439	if $ce->num_interfaces != 0
440		set $ce = $ce->interfaces[0]
441		printf " extends %s", $ce->name->val
442	else
443		set $ce = 0
444	end
445end
446
447define print_inh
448	set $ce = $arg0
449	set $depth = 0
450	while $ce != 0
451		set $tmp = $depth
452		while $tmp != 0
453			printf " "
454			set $tmp = $tmp - 1
455		end
456		set $depth = $depth + 1
457		if $ce->ce_flags & 0x80
458			____print_inh_iface $ce
459		else
460			____print_inh_class $ce
461		end
462		printf " {\n"
463	end
464	while $depth != 0
465		set $tmp = $depth
466		while $tmp != 1
467			printf " "
468			set $tmp = $tmp - 1
469		end
470		printf "}\n"
471		set $depth = $depth - 1
472	end
473end
474
475define print_pi
476	set $pi = (zend_property_info *)$arg0
477	set $initial_offset = ((uint32_t)(zend_uintptr_t)(&((zend_object*)0)->properties_table[(0)]))
478	set $ptr_to_val = (zval*)((char*)$pi->ce->default_properties_table + $pi->offset - $initial_offset)
479	printf "[%p] {\n", $pi
480	printf "    offset = %p\n", $pi->offset
481	printf "    ce = [%p] %s\n", $pi->ce, $pi->ce->name->val
482	printf "    flags = 0x%x (", $pi->flags
483	if $pi->flags & 0x100
484		printf "ZEND_ACC_PUBLIC"
485	else
486		if $pi->flags & 0x200
487			printf "ZEND_ACC_PROTECTED"
488		else
489			if $pi->flags & 0x400
490				printf "ZEND_ACC_PRIVATE"
491			else
492				if $pi->flags & 0x800
493					printf "ZEND_ACC_EARLY_BINDING"
494				else
495					if $pi->flags & 0x20000
496						printf "ZEND_ACC_SHADOW"
497					end
498				end
499			end
500		end
501	end
502	printf ")\n"
503	printf "    name  = "
504	print_zstr $pi->name
505	printf "    default value: "
506	printzv $ptr_to_val
507	printf "}\n"
508end
509
510document print_pi
511	Takes a pointer to an object's property and prints the property information
512	usage: print_pi <ptr>
513end
514
515define ____print_str
516	set $tmp = 0
517	set $str = $arg0
518	if $argc > 2
519		set $maxlen = $arg2
520	else
521		set $maxlen = 256
522	end
523
524	printf "\""
525	while $tmp < $arg1 && $tmp < $maxlen
526		if $str[$tmp] > 31 && $str[$tmp] < 127
527			printf "%c", $str[$tmp]
528		else
529			printf "\\%o", $str[$tmp]
530		end
531		set $tmp = $tmp + 1
532	end
533	if $tmp != $arg1
534		printf "..."
535	end
536	printf "\""
537end
538
539define printzn
540	____executor_globals
541	set $ind = 0
542	set $znode = $arg0
543	if $znode->op_type == 1
544		set $optype = "IS_CONST"
545	end
546	if $znode->op_type == 2
547		set $optype = "IS_TMP_VAR"
548	end
549	if $znode->op_type == 4
550		set $optype = "IS_VAR"
551	end
552	if $znode->op_type == 8
553		set $optype = "IS_UNUSED"
554	end
555
556	printf "[%p] %s", $znode, $optype
557
558	if $znode->op_type == 1
559		printf ": "
560		____printzv &$znode->u.constant 0
561	end
562	if $znode->op_type == 2
563		printf ": "
564		set $tvar = (union _temp_variable *)((char *)$eg.current_execute_data->Ts + $znode->u.var)
565		____printzv ((union _temp_variable *)$tvar)->tmp_var 0
566	end
567	if $znode->op_type == 4
568		printf ": "
569		set $tvar = (union _temp_variable *)((char *)$eg.current_execute_data->Ts + $znode->u.var)
570		____printzv *$tvar->var.ptr_ptr 0
571	end
572	if $znode->op_type == 8
573		printf "\n"
574	end
575end
576
577document printzn
578	print type and content of znode.
579	usage: printzn &opline->op1
580end
581
582define printzops
583	printf "op1 => "
584	printzn &execute_data->opline.op1
585	printf "op2 => "
586	printzn &execute_data->opline.op2
587	printf "result => "
588	printzn &execute_data->opline.result
589end
590
591document printzops
592	dump operands of the current opline
593end
594
595define print_zstr
596	set $zstr = (zend_string *)$arg0
597	if $argc == 2
598		set $maxlen = $arg1
599	else
600		set $maxlen = $zstr->len
601	end
602	printf "string(%d) ", $zstr->len
603	____print_str $zstr->val $zstr->len $maxlen
604	printf "\n"
605end
606
607document print_zstr
608	print the length and contents of a zend string
609	usage: print_zstr <ptr> [max length]
610end
611
612define zbacktrace
613	____executor_globals
614	dump_bt $eg.current_execute_data
615end
616
617document zbacktrace
618	prints backtrace.
619	This command is almost a short cut for
620	> (gdb) ____executor_globals
621	> (gdb) dump_bt $eg.current_execute_data
622end
623
624define lookup_root
625	set $found = 0
626	if gc_globals->roots
627		set $current = gc_globals->roots->next
628		printf "looking ref %p in roots\n", $arg0
629		while $current != &gc_globals->roots
630			if $current->ref == $arg0
631				set $found = $current
632				break
633			end
634			set $current = $current->next
635		end
636		if $found != 0
637			printf "found root %p\n", $found
638		else
639			printf "not found\n"
640		end
641	end
642end
643
644document lookup_root
645	lookup a refcounted in root
646	usage: lookup_root [ptr].
647end
648