diff options
Diffstat (limited to 'itrace.s')
-rw-r--r-- | itrace.s | 419 |
1 files changed, 419 insertions, 0 deletions
diff --git a/itrace.s b/itrace.s new file mode 100644 index 0000000..80b53b7 --- /dev/null +++ b/itrace.s @@ -0,0 +1,419 @@ + +#undef DEBUG_PROFILER + +#define MODULE_NAMES + +#define d0 %eax +#define d1 %ebx +#define a0 %ecx +#define a1 %edx +#define a2 %ebp +#define a3 %esi +#define a4 %edi +#define sp %esp + +#if defined(_WINDOWS_) +# define align(n) .align (1<<n) +#else +# define align(n) .align n +#endif + + .global init_profiler + .global profile_r + .global profile_l + .global profile_l2 + .global profile_n + .global profile_n2 + .global profile_s + .global profile_s2 + .global profile_t + .global write_profile_information + .global write_profile_stack + + .global @allocate_memory + .global __STRING__ + .global writeFC + .global writeFI + .global print_error + .global @ab_stack_size + .global @ew_print_string + .global @ew_print_char + .global @stack_trace_depth + +#define next 0 +#define name 4 +#define FunctionProfile 8 + + .text +profile_t: + push a0 + mov profile_stack_pointer,a0 + + push d1 + mov -4(a0),d1 + + sub $4,a0 + + mov a0,profile_stack_pointer + + pop d1 + pop a0 + ret + +profile_r: + push a0 + mov profile_stack_pointer,a0 + + push d1 + mov -4(a0),d1 + + sub $4,a0 + + mov a0,profile_stack_pointer + + pop d1 + pop a0 + ret + +profile_l: + push d1 + mov (a2),d1 + + test d1,d1 + je allocate_function_profile_record_l +allocate_function_profile_record_lr: + push a0 + + mov profile_stack_pointer,a0 + +#ifdef DEBUG_PROFILER + testl (d1),d1 +#endif + mov d1,(a0) + add $4,a0 + + mov a0,profile_stack_pointer + + pop a0 + pop d1 + ret + +allocate_function_profile_record_l: + call allocate_function_profile_record + jmp allocate_function_profile_record_lr + +profile_l2: + push d1 + mov (a2),d1 + + test d1,d1 + je allocate_function_profile_record_l2 +allocate_function_profile_record_l2r: + push a0 + + mov profile_stack_pointer,a0 + +#ifdef DEBUG_PROFILER + testl (d1),d1 +#endif + mov d1,(a0) + mov d1,4(a0) + add $8,a0 + + mov a0,profile_stack_pointer + + pop a0 + pop d1 + ret + +allocate_function_profile_record_l2: + call allocate_function_profile_record + jmp allocate_function_profile_record_l2r + +profile_n: + push d1 + mov (a2),d1 + + test d1,d1 + je allocate_function_profile_record_n +allocate_function_profile_record_nr: + push a0 + + mov profile_stack_pointer,a0 + +#ifdef DEBUG_PROFILER + testl (d1),d1 +#endif + mov d1,(a0) + add $4,a0 + + mov a0,profile_stack_pointer + + pop a0 + pop d1 + ret + +allocate_function_profile_record_n: + call allocate_function_profile_record + jmp allocate_function_profile_record_nr + +profile_n2: + push d1 + mov (a2),d1 + + test d1,d1 + je allocate_function_profile_record_n2 +allocate_function_profile_record_n2r: + push a0 + + mov profile_stack_pointer,a0 + +#ifdef DEBUG_PROFILER + testl (d1),d1 +#endif + mov d1,(a0) + mov d1,4(a0) + add $8,a0 + + mov a0,profile_stack_pointer + + pop a0 + pop d1 + ret + +allocate_function_profile_record_n2: + call allocate_function_profile_record + jmp allocate_function_profile_record_n2r + +profile_s2: + push d1 + mov (a2),d1 + + test d1,d1 + je allocate_function_profile_record_s2 +allocate_function_profile_record_s2r: + push a0 + + mov profile_stack_pointer,a0 + +#ifdef DEBUG_PROFILER + testl (d1),d1 +#endif + movl d1,(a0) + movl d1,4(a0) + add $8,a0 + mov a0,profile_stack_pointer + + pop a0 + pop d1 + ret + +allocate_function_profile_record_s2: + call allocate_function_profile_record + jmp allocate_function_profile_record_s2r + +profile_s: + push d1 + movl (a2),d1 + + test d1,d1 + je allocate_function_profile_record_s +allocate_function_profile_record_sr: + push a0 + + mov profile_stack_pointer,a0 + +#ifdef DEBUG_PROFILER + testl (d1),d1 +#endif + movl d1,(a0) + add $4,a0 + + mov a0,profile_stack_pointer + + pop a0 + pop d1 + ret + +allocate_function_profile_record_s: + call allocate_function_profile_record + jmp allocate_function_profile_record_sr + + +/ argument: a2: function name adress-4 +/ result: d1: function profile record adress + +allocate_function_profile_record: + push d0 + mov global_n_free_records_in_block,d0 + mov global_last_allocated_block,d1 + + test d0,d0 + jne no_alloc + + push d1 + push a0 + push a1 + + pushl $512*FunctionProfile + call @allocate_memory + add $4,sp + + test d0,d0 + + pop a1 + pop a0 + pop d1 + + je no_memory + + mov d0,d1 + mov $512,d0 + mov d1,global_last_allocated_block + +no_alloc: + dec d0 + mov d0,global_n_free_records_in_block + lea FunctionProfile(d1),d0 + mov d0,global_last_allocated_block + + mov global_profile_records,d0 + mov a2,name(d1) + + mov d0,next(d1) + mov d1,global_profile_records + + mov d1,(a2) + pop d0 + ret + +no_memory: + movl $not_enough_memory_for_profiler,a2 + pop d0 + jmp print_error + +write_profile_information: + ret + +write_profile_stack: + mov profile_stack_pointer,d0 + + test d0,d0 + je stack_not_initialised + + push d0 + + push $stack_trace_string + call @ew_print_string + add $4,sp + + pop d0 + +/ mov $12,a2 + movl @stack_trace_depth,a2 +write_functions_on_stack: + mov -4(d0),d1 + sub $4,d0 + + test d1,d1 + je end_profile_stack + + push d0 + mov name(d1),a0 + + push a2 + add $4,a0 + + push a0 + call @ew_print_string + add $4,sp + + pushl $10 + call @ew_print_char + add $4,sp + + pop a2 + pop d0 + + sub $1,a2 + jne write_functions_on_stack + +end_profile_stack: +stack_not_initialised: + ret + +init_profiler: + pushl @ab_stack_size + call @allocate_memory + add $4,sp + + test d0,d0 + je init_profiler_error + + push d0 + + mov $start_string,a2 + call allocate_function_profile_record + + pop a1 + + mov d1,4(a1) + movl $0,(a1) + add $8,a1 + mov a1,profile_stack_pointer + + mov end_heap,a1 + sub a4,a1 + add $32,a1 + mov a1,global_n_bytes_free + ret + +init_profiler_error: + movl $0,profile_stack_pointer + movl $not_enough_memory_for_profile_stack,a2 + jmp print_error + + .data + align (2) + +global_n_free_records_in_block: .long 0 +/ 0 n free records in block +global_last_allocated_block: .long 0 +/ 4 latest allocated block +global_profile_records: .long 0 +/ 8 profile record list +profile_stack_pointer: .long 0 +global_n_bytes_free: .long 0 + + align (2) +@stack_trace_depth: + .long 12 +#ifdef MODULE_NAMES +# if 0 +/ m_system also defined in cgistartup.s +m_system: + .long 6 + .ascii "System" + .byte 0 + .byte 0 +# endif + .long m_system +#endif +start_string: + .long 0 + .asciz "start" + align (2) +not_enough_memory_for_profile_stack: + .ascii "not enough memory for profile stack" + .byte 10 + .byte 0 +not_enough_memory_for_profiler: + .ascii "not enough memory for profiler" + .byte 10 + .byte 0 +stack_trace_string: + .ascii "Stack trace:" + .byte 10 + .byte 0 + + align (2) |