diff options
Diffstat (limited to 'pprofile.a')
-rw-r--r-- | pprofile.a | 1407 |
1 files changed, 1407 insertions, 0 deletions
diff --git a/pprofile.a b/pprofile.a new file mode 100644 index 0000000..7adc9f2 --- /dev/null +++ b/pprofile.a @@ -0,0 +1,1407 @@ + + string asis + + macro + lea &r,&a + lwz &r,&a{TC}(RTOC) + endm + +MACOSX set 1 +; POWER601 set 1 +ALLOCATION_PROFILE set 1 +USE_TEMPORARY_MEMORY set 1 +CHECK_STACK_OVERFLOWS set 0 +MODULE_NAMES set 1 + + if POWER601 + macro + time_hi &r + dialect Power + mfrtcu &r + dialect PowerPC + endm + + macro + time_lo &r + dialect Power + mfrtcl &r + dialect PowerPC + endm + else + macro + time_hi &r + mftbu &r + endm + + macro + time_lo &r + mftb &r + endm + endif + +d0: set r24 +d1: set r25 +d2: set r26 +d3: set r27 +d4: set r28 +d5: set r29 +d6: set r30 +d7: set r31 + +a0: set r23 +a1: set r22 +a2: set r21 +a3: set r20 +a4: set r19 +a5: set r18 +a6: set r17 + +o0: set r3 +o1: set r4 +o2: set r5 +o3: set r6 +o4: set r7 +o5: set r8 + +g2: set r9 +g3: set r10 + +g0: set r11 +g1: set r12 + +int_reg set r16 +char_reg set r15 +real_reg set r14 +bool_reg set r13 + + if POWER601 +lo1e9 set 1000000000 % 65536 +hi1e9 set (1000000000 / 65536)+1 + endif + + export init_profiler + export profile_r + export profile_l + export profile_l2 + export profile_n + export profile_n2 + export profile_s + export profile_s2 + export profile_t + export profile_ti + export write_profile_information + export write_profile_stack + + if USE_TEMPORARY_MEMORY + import .TempNewHandle + import .TempHLock + import .TempHUnlock + import .TempDisposeHandle + else + import .NewPtr + endif + import .Gestalt + import __STRING__ + import openF + import closeF + import writeFC + import writeFI + import print_error + import new_file_creator + import stack_size + import .er_print_string + import .er_print_char + import .create_profile_file_name + if CHECK_STACK_OVERFLOWS + import .Debugger + endif + +FunctionProfile: record +next: ds.l 1 +time_hi: ds.l 1 +time_lo: ds.l 1 +n_profiler_calls: ds.l 1 +n_strict_calls: ds.l 1 +n_lazy_calls: ds.l 1 +n_curried_calls: ds.l 1 +n_words_allocated: ds.l 1 +name: ds.l 1 + endr + + csect .profile_t +profile_ti: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + lea r5,profile_globals + b profile_t_ + +profile_t: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + mflr r12 + lea r5,profile_globals + mtctr r12 + mtlr r0 +profile_t_: + lwz r6,Globals.stack_pointer(r5) + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + lwzu r4,-4(r6) + stw r6,Globals.stack_pointer(r5) + stw r4,Globals.last_tail_call(r5) + + if POWER601 + sub. r10,r10,r8 + sub r9,r9,r7 + bge+ @no_borrow + addis r10,r10,hi1e9 + addi r10,r10,lo1e9 + subi r9,r9,1 +@no_borrow: + else + subc r10,r10,r8 + subfe r9,r7,r9 + endif + lwz r8,FunctionProfile.time_lo(r4) + lwz r7,FunctionProfile.time_hi(r4) + + if POWER601 + add r8,r8,r10 + add r7,r7,r9 + + subis r9,r8,hi1e9 + cmpwi 0,r9,lo1e9 + + lwz r6,FunctionProfile.n_profiler_calls(r4) + + blt+ @no_carry + + subi r8,r9,lo1e9 + addi r7,r7,1 + +@no_carry: + else + addc r8,r8,r10 + lwz r6,FunctionProfile.n_profiler_calls(r4) + adde r7,r7,r9 + endif + addi r6,r6,1 + stw r7,FunctionProfile.time_hi(r4) + stw r8,FunctionProfile.time_lo(r4) + stw r6,FunctionProfile.n_profiler_calls(r4) + + if ALLOCATION_PROFILE + lwz r11,Globals.n_words_free(r5) + stw d7,Globals.n_words_free(r5) + lwz r12,FunctionProfile.n_words_allocated(r4) + sub r11,r11,d7 + add r12,r12,r11 + stw r12,FunctionProfile.n_words_allocated(r4) + endif + +@store_clock: + time_hi r9 + stw r9,Globals.time_hi(r5) + time_lo r10 + time_hi r4 + stw r10,Globals.time_lo(r5) + cmpw 0,r4,r9 + beqctr+ + + b @store_clock + + csect .profile_r +profile_r: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + lea r5,profile_globals + + lwz r6,Globals.stack_pointer(r5) + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + lwzu r4,-4(r6) + li r3,0 + stw r6,Globals.stack_pointer(r5) + stw r3,Globals.last_tail_call(r5) + + if POWER601 + sub. r10,r10,r8 + sub r9,r9,r7 + bge+ @no_borrow + addis r10,r10,hi1e9 + addi r10,r10,lo1e9 + subi r9,r9,1 +@no_borrow: + else + subc r10,r10,r8 + subfe r9,r7,r9 + endif + + lwz r8,FunctionProfile.time_lo(r4) + lwz r7,FunctionProfile.time_hi(r4) + + if POWER601 + add r8,r8,r10 + add r7,r7,r9 + + subis r9,r8,hi1e9 + cmpwi 0,r9,lo1e9 + + lwz r6,FunctionProfile.n_profiler_calls(r4) + + blt+ @no_carry + + subi r8,r9,lo1e9 + addi r7,r7,1 + +@no_carry: + else + addc r8,r8,r10 + lwz r6,FunctionProfile.n_profiler_calls(r4) + adde r7,r7,r9 + endif + + addi r6,r6,1 + stw r7,FunctionProfile.time_hi(r4) + stw r8,FunctionProfile.time_lo(r4) + stw r6,FunctionProfile.n_profiler_calls(r4) + + if ALLOCATION_PROFILE + lwz r11,Globals.n_words_free(r5) + stw d7,Globals.n_words_free(r5) + lwz r12,FunctionProfile.n_words_allocated(r4) + sub r11,r11,d7 + add r12,r12,r11 + stw r12,FunctionProfile.n_words_allocated(r4) + endif + +@store_clock: + time_hi r9 + stw r9,Globals.time_hi(r5) + time_lo r10 + time_hi r4 + stw r10,Globals.time_lo(r5) + cmpw 0,r4,r9 + beqlr+ + + b @store_clock + + csect .profile_l +profile_l: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + mflr r12 + lea r5,profile_globals + lwz r4,0(r3) + mtctr r12 + + cmpwi 0,r4,0 + beql allocate_function_profile_record + + lwz r3,Globals.last_tail_call(r5) + lwz r6,Globals.stack_pointer(r5) + cmpwi 0,r3,0 + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + bne @use_tail_calling_function + + lwz r3,-4(r6) +@c_use_tail_calling_function: + + stw r4,0(r6) + addi r6,r6,4 + if CHECK_STACK_OVERFLOWS + lwz r12,Globals.end_profile_stack(r5) + endif + stw r6,Globals.stack_pointer(r5) + if CHECK_STACK_OVERFLOWS + cmpw r6,r12 + bge profile_stack_overflow + endif + lwz r6,FunctionProfile.n_curried_calls(r4) + mtlr r0 + addi r6,r6,1 + stw r6,FunctionProfile.n_curried_calls(r4) + b profile_n_ + +@use_tail_calling_function: + li r12,0 + stw r12,Globals.last_tail_call(r5) + b @c_use_tail_calling_function + + csect .profile_l2 +profile_l2: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + mflr r12 + lea r5,profile_globals + lwz r4,0(r3) + mtctr r12 + + cmpwi 0,r4,0 + beql allocate_function_profile_record + + lwz r3,Globals.last_tail_call(r5) + lwz r6,Globals.stack_pointer(r5) + cmpwi 0,r3,0 + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + bne @use_tail_calling_function + + lwz r3,-4(r6) +@c_use_tail_calling_function: + + stw r4,0(r6) + stw r4,4(r6) + addi r6,r6,8 + if CHECK_STACK_OVERFLOWS + lwz r12,Globals.end_profile_stack(r5) + endif + stw r6,Globals.stack_pointer(r5) + if CHECK_STACK_OVERFLOWS + cmpw r6,r12 + bge profile_stack_overflow + endif + + lwz r6,FunctionProfile.n_curried_calls(r4) + mtlr r0 + addi r6,r6,1 + stw r6,FunctionProfile.n_curried_calls(r4) + b profile_n_ + +@use_tail_calling_function: + li r12,0 + stw r12,Globals.last_tail_call(r5) + b @c_use_tail_calling_function + + csect .profile_n +profile_n: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + mflr r12 + lea r5,profile_globals + lwz r4,0(r3) + mtctr r12 + + cmpwi 0,r4,0 + beql allocate_function_profile_record + + lwz r3,Globals.last_tail_call(r5) + lwz r6,Globals.stack_pointer(r5) + cmpwi 0,r3,0 + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + bne @use_tail_calling_function + + lwz r3,-4(r6) +@c_use_tail_calling_function: + + stw r4,0(r6) + addi r6,r6,4 + if CHECK_STACK_OVERFLOWS + lwz r12,Globals.end_profile_stack(r5) + endif + stw r6,Globals.stack_pointer(r5) + if CHECK_STACK_OVERFLOWS + cmpw r6,r12 + bge profile_stack_overflow + endif + + lwz r6,FunctionProfile.n_lazy_calls(r4) + mtlr r0 + addi r6,r6,1 + stw r6,FunctionProfile.n_lazy_calls(r4) + b profile_n_ + +@use_tail_calling_function: + li r12,0 + stw r12,Globals.last_tail_call(r5) + b @c_use_tail_calling_function + + csect .profile_n2 +profile_n2: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + mflr r12 + lea r5,profile_globals + lwz r4,0(r3) + mtctr r12 + + cmpwi 0,r4,0 + beql allocate_function_profile_record + + lwz r3,Globals.last_tail_call(r5) + lwz r6,Globals.stack_pointer(r5) + cmpwi 0,r3,0 + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + bne @use_tail_calling_function + + lwz r3,-4(r6) +@c_use_tail_calling_function: + + stw r4,0(r6) + stw r4,4(r6) + addi r6,r6,8 + if CHECK_STACK_OVERFLOWS + lwz r12,Globals.end_profile_stack(r5) + endif + stw r6,Globals.stack_pointer(r5) + if CHECK_STACK_OVERFLOWS + cmpw r6,r12 + bge profile_stack_overflow + endif + + lwz r6,FunctionProfile.n_lazy_calls(r4) + mtlr r0 + addi r6,r6,1 + stw r6,FunctionProfile.n_lazy_calls(r4) + b profile_n_ + +@use_tail_calling_function: + li r12,0 + stw r12,Globals.last_tail_call(r5) + b @c_use_tail_calling_function + + csect .profile_s2 +profile_s2: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + mflr r12 + lea r5,profile_globals + lwz r4,0(r3) + mtctr r12 + + cmpwi 0,r4,0 + beql allocate_function_profile_record + + lwz r3,Globals.last_tail_call(r5) + lwz r6,Globals.stack_pointer(r5) + cmpwi 0,r3,0 + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + bne @use_tail_calling_function + + lwz r3,-4(r6) +@c_use_tail_calling_function: + + stw r4,0(r6) + stw r4,4(r6) + addi r6,r6,8 + if CHECK_STACK_OVERFLOWS + lwz r12,Globals.end_profile_stack(r5) + endif + stw r6,Globals.stack_pointer(r5) + if CHECK_STACK_OVERFLOWS + cmpw r6,r12 + bge profile_stack_overflow + endif + b profile_s_ + +@use_tail_calling_function: + li r12,0 + stw r12,Globals.last_tail_call(r5) + b @c_use_tail_calling_function + + csect .profile_s +profile_s: +@read_clock: + time_hi r9 + time_lo r10 + time_hi r4 + cmpw 0,r4,r9 + bne- @read_clock + + mflr r12 + lea r5,profile_globals + lwz r4,0(r3) + mtctr r12 + + cmpwi 0,r4,0 + beql allocate_function_profile_record + + lwz r3,Globals.last_tail_call(r5) + lwz r6,Globals.stack_pointer(r5) + cmpwi 0,r3,0 + + lwz r7,Globals.time_hi(r5) + lwz r8,Globals.time_lo(r5) + + bne use_tail_calling_function0 + + lwz r3,-4(r6) +c_use_tail_calling_function0: + + stw r4,0(r6) + addi r6,r6,4 + if CHECK_STACK_OVERFLOWS + lwz r12,Globals.end_profile_stack(r5) + endif + stw r6,Globals.stack_pointer(r5) + if CHECK_STACK_OVERFLOWS + cmpw r6,r12 + bge profile_stack_overflow + endif + +profile_s_: + lwz r6,FunctionProfile.n_strict_calls(r4) + mtlr r0 + addi r6,r6,1 + stw r6,FunctionProfile.n_strict_calls(r4) + +profile_n_: + if POWER601 + sub. r10,r10,r8 + sub r9,r9,r7 + bge+ @no_borrow + addis r10,r10,hi1e9 + addi r10,r10,lo1e9 + subi r9,r9,1 +@no_borrow: + else + subc r10,r10,r8 + subfe r9,r7,r9 + endif + + lwz r8,FunctionProfile.time_lo(r3) + lwz r7,FunctionProfile.time_hi(r3) + + if POWER601 + add r8,r8,r10 + add r7,r7,r9 + + subis r9,r8,hi1e9 + cmpwi 0,r9,lo1e9 + + lwz r6,FunctionProfile.n_profiler_calls(r4) + + blt+ @no_carry + + subi r8,r9,lo1e9 + addi r7,r7,1 + +@no_carry: + else + addc r8,r8,r10 + lwz r6,FunctionProfile.n_profiler_calls(r4) + adde r7,r7,r9 + endif + addi r6,r6,1 + stw r7,FunctionProfile.time_hi(r3) + stw r8,FunctionProfile.time_lo(r3) + stw r6,FunctionProfile.n_profiler_calls(r4) + + if ALLOCATION_PROFILE + lwz r11,Globals.n_words_free(r5) + stw d7,Globals.n_words_free(r5) + lwz r12,FunctionProfile.n_words_allocated(r3) + sub r11,r11,d7 + add r12,r12,r11 + stw r12,FunctionProfile.n_words_allocated(r3) + endif + +@store_clock: + time_hi r9 + stw r9,Globals.time_hi(r5) + time_lo r10 + time_hi r4 + stw r10,Globals.time_lo(r5) + cmpw 0,r4,r9 + beqctr+ + + b @store_clock + +use_tail_calling_function0: + li r12,0 + stw r12,Globals.last_tail_call(r5) + b c_use_tail_calling_function0 + +allocate_function_profile_record: + lwz r6,Globals.n_free_records_in_block(r5) + lwz r4,Globals.last_allocated_block(r5) + cmpwi 0,r6,0 + bne+ no_alloc + + stw r0,-4(sp) + stw r3,-8(sp) + stw r9,-12(sp) + stw r10,-16(sp) + mfctr r11 + stw r11,-20(sp) + mflr r12 + stw r12,-24(sp) + + if USE_TEMPORARY_MEMORY + li r3,(128*FunctionProfile)+4 + else + li r3,128*FunctionProfile + endif + if MACOSX + mr g0,sp + ori sp,sp,28 + stwu g0,-(64+32+28)(sp) + else + stwu sp,-(64+32)(sp) + endif + if USE_TEMPORARY_MEMORY + bl allocate_temp_memory_handle + else + bl .NewPtr + nop + endif + if MACOSX + lwz sp,0(sp) + else + addi sp,sp,64+32 + endif + and. r4,r3,r3 + + lwz r12,-24(sp) + lwz r11,-20(sp) + mtlr r12 + lwz r10,-16(sp) + mtctr r11 + lwz r9,-12(sp) + lwz r3,-8(sp) + lwz r0,-4(sp) + + lea r5,profile_globals + + beq profiler_memory_error + + if USE_TEMPORARY_MEMORY + lwz r6,Globals.temp_handle_list(r5) + stw r4,Globals.temp_handle_list(r5) + lwz r4,0(r4) + stw r6,0(r4) + addi r4,r4,4 + endif + li r6,128 + stw r4,Globals.last_allocated_block(r5) + +no_alloc: + subi r6,r6,1 + stw r6,Globals.n_free_records_in_block(r5) + addi r7,r4,FunctionProfile + stw r7,Globals.last_allocated_block(r5) + + lwz r6,Globals.profile_records(r5) + li r8,0 + stw r8,FunctionProfile.time_hi(r4) + stw r8,FunctionProfile.time_lo(r4) + stw r8,FunctionProfile.n_profiler_calls(r4) + stw r8,FunctionProfile.n_strict_calls(r4) + stw r8,FunctionProfile.n_lazy_calls(r4) + stw r8,FunctionProfile.n_curried_calls(r4) + stw r8,FunctionProfile.n_words_allocated(r4) + stw r6,FunctionProfile.next(r4) + stw r4,Globals.profile_records(r5) + stw r3,FunctionProfile.name(r4) + + stw r4,0(r3) + blr + + csect .write_profile_information +write_profile_information: + lea o0,profile_file_name + + mflr r0 + stwu r0,-4(sp) + if MACOSX + mr g0,sp + ori sp,sp,28 + stwu g0,-(64+28)(sp) + else + stwu sp,-64(sp) + endif + bl .create_profile_file_name + nop + if MACOSX + lwz sp,0(sp) + lwz r0,0(sp) + addi sp,sp,4 + else + lwz r0,64(sp) + addi sp,sp,68 + endif + mtlr r0 + + lea d3,new_file_creator + li d5,'T'*256+'I' + lwz d4,0(d3) + addis d5,d5,'P'*256+'R' + stw d5,0(d3) + + li d0,1 + lea a0,profile_file_name + + mflr r0 + stwu r0,-4(sp) + bl openF + mtlr r0 + + stw d4,0(d3) + + cmpwi 0,d2,0 + beq cannot_open + + mflr r0 + li d3,0 + stw r0,-4(sp) + stwu d3,-8(sp) + + if MACOSX + mr g0,sp + ori sp,sp,28 + stwu g0,-(64+28)(sp) + else + stwu sp,-64(sp) + endif + stw d3,64(sp) + li r3,'u'*256+'t' + addi r4,sp,64 + addis r3,r3,'c'*256+'p' + bl .Gestalt + nop + + lwz d2,64(sp) + stwu r0,-4(sp) + bl writeFI_space + mtlr r0 + + stw d3,64(sp) + li r3,'l'*256+'k' + addi r4,sp,64 + addis r3,r3,'p'*256+'c' + bl .Gestalt + nop + + lwz d2,64(sp) + stwu r0,-4(sp) + bl writeFI_space + mtlr r0 + + stw d3,64(sp) + li r3,'l'*256+'k' + addi r4,sp,64 + addis r3,r3,'b'*256+'c' + bl .Gestalt + nop + + lwz d2,64(sp) + stwu r0,-4(sp) + bl writeFI + mtlr r0 + + li d2,13 + stwu r0,-4(sp) + bl writeFC + mtlr r0 + + if MACOSX + lwz sp,0(sp) + lwz r0,4(sp) + addi sp,sp,8 + else + lwz r0,68(sp) + addi sp,sp,72 + endif + mtlr r0 + + lea d2,profile_globals + lwz d2,Globals.profile_records(d2) + +write_profile_lp: + cmpwi 0,d2,0 + beq end_list + + lwz d3,FunctionProfile.name(d2) + stwu d2,-4(sp) + +#if MODULE_NAMES + stwu d3,-4(sp) + + lwz d3,-4(d3) + lwz d2,0(d3) + addi d3,d3,3 + +write_module_name_lp: + subic. d2,d2,1 + blt end_module_name + + stw d2,-4(sp) + lbzu d2,1(d3) + + mflr r0 + + stw d3,-8(sp) + + stwu r0,-12(sp) + bl writeFC + mtlr r0 + + lwz d2,4(sp) + lwz d3,0(sp) + addi sp,sp,8 + b write_module_name_lp + +end_module_name: + li d2,' ' + + mflr r0 + stwu r0,-4(sp) + bl writeFC + mtlr r0 + + lwz d3,0(sp) + addi sp,sp,4 +#endif + + addi d3,d3,3 + +write_function_name_lp: + lbzu d2,1(d3) + cmpwi 0,d2,0 + beq end_function_name + + stw d3,-4(sp) + + mflr r0 + stwu r0,-8(sp) + bl writeFC + mtlr r0 + + lwz d3,0(sp) + addi sp,sp,4 + b write_function_name_lp + +end_function_name: + li d2,' ' + + mflr r0 + stwu r0,-4(sp) + bl writeFC + + lwz d2,0(sp) + lwz d2,FunctionProfile.n_strict_calls(d2) + stwu r0,-4(sp) + bl writeFI_space + + lwz d2,0(sp) + lwz d2,FunctionProfile.n_lazy_calls(d2) + stwu r0,-4(sp) + bl writeFI_space + + lwz d2,0(sp) + lwz d2,FunctionProfile.n_curried_calls(d2) + stwu r0,-4(sp) + bl writeFI_space + + lwz d2,0(sp) + lwz d2,FunctionProfile.n_profiler_calls(d2) + stwu r0,-4(sp) + bl writeFI_space + + lwz d2,0(sp) + lwz d2,FunctionProfile.n_words_allocated(d2) + stwu r0,-4(sp) + bl writeFI_space + + lwz d2,0(sp) + lwz d2,FunctionProfile.time_hi(d2) + stwu r0,-4(sp) + bl writeFI_space + + lwz d2,0(sp) + lwz d2,FunctionProfile.time_lo(d2) + stwu r0,-4(sp) + bl writeFI + + li d2,13 + stwu r0,-4(sp) + bl writeFC + mtlr r0 + + lwz d2,0(sp) + addi sp,sp,4 + lwz d2,FunctionProfile.next(d2) + b write_profile_lp + +writeFI_space: + mflr r0 + stwu r0,-4(sp) + bl writeFI + mtlr r0 + + li d2,' ' + b writeFC + +end_list: + mflr r0 + stwu r0,-4(sp) + bl closeF + mtlr r0 + +cannot_open: + + if USE_TEMPORARY_MEMORY + mflr r0 + if MACOSX + mr g0,sp + ori sp,sp,28 + stwu g0,-(96+28)(sp) + else + stwu sp,-96(sp) + endif + stw r0,96-4(sp) + lea r5,profile_globals + lwz r3,Globals.profile_stack_handle(r5) + bl free_temp_memory_handle + + lea r5,profile_globals + + stw r31,96-8(sp) + + lwz r31,Globals.temp_handle_list(r5) + b free_temp_handles + +free_temp_handles_lp: + mr r3,r31 + lwz r31,0(r31) + lwz r31,0(r31) + bl free_temp_memory_handle + +free_temp_handles: + cmpwi 0,r31,0 + bne free_temp_handles_lp + + lwz r31,96-8(sp) + + lwz r0,96-4(sp) + if MACOSX + lwz sp,0(sp) + else + addi sp,sp,96 + endif + mtlr r0 + endif + lwz r0,0(sp) + addi sp,sp,4 + blr + + csect .write_profile_stack +write_profile_stack: + mflr r0 + lea d0,profile_globals + stwu r0,-4(sp) + lwz d0,Globals.stack_pointer(d0) + + cmpwi 0,d0,0 + beq @stack_not_initialised + + if MACOSX + mr g0,sp + ori sp,sp,28 + stwu g0,-(64+28)(sp) + else + stwu sp,-64(sp) + endif + lea o0,stack_trace_string + bl .er_print_string + nop + if MACOSX + lwz sp,0(sp) + else + addi sp,sp,64 + endif + + if 1 + li d2,12 + else + li d2,24 + endif +@write_functions_on_stack + lwzu d1,-4(d0) + cmpwi 0,d1,0 + beq @end_profile_stack + + lwz o0,FunctionProfile.name(d1) + + if MACOSX + mr g0,sp + ori sp,sp,28 + stwu g0,-(64+28)(sp) + else + stwu sp,-64(sp) + endif + addi o0,o0,4 + bl .er_print_string + nop + li o0,13 + bl .er_print_char + nop + if MACOSX + lwz sp,0(sp) + else + addi sp,sp,64 + endif + + subic. d2,d2,1 + if 0 + b @write_functions_on_stack + else + bne @write_functions_on_stack + endif + +@end_profile_stack: +@stack_not_initialised: + lwz r0,0(sp) + mtlr r0 + lwz r0,4(sp) + addi sp,sp,8 + blr + + csect .init_profiler +init_profiler: + if 0 + mflr r0 + stw r0,-4(sp) + stwu sp,-64(sp) + + bl .Debugger + nop + + lwz r0,64-4(sp) + addi sp,sp,64 + mtlr r0 + endif + + mflr r0 + stwu r0,-4(sp) + + if MACOSX + subi sp,sp,8 + mr g0,sp + ori sp,sp,28 + stwu g0,-(64+28)(sp) + else + stwu sp,-72(sp) + endif + li r3,0 + addi r4,sp,64 + stw r3,64(sp) + li r3,'u'*256+'t' + addis r3,r3,'c'*256+'p' + bl .Gestalt + nop + lwz r3,64(sp) + if MACOSX + lwz sp,0(sp) + addi sp,sp,8 + else + addi sp,sp,72 + endif + + cmpwi 0,r3,257 + if POWER601 + bne init_profiler_error1 + else + beq init_profiler_error1 + endif + + if 1 + lea r3,stack_size + lwz r3,0(r3) + else + li r3, (512*1024) % 65536 + addis r3,r3,(512*1024) / 65536 + endif + + if MACOSX + mr g0,sp + ori sp,sp,28 + stwu g0,-(64+28)(sp) + else + stwu sp,-64(sp) + endif + if USE_TEMPORARY_MEMORY + bl allocate_temp_memory_handle + else + bl .NewPtr + nop + endif + if MACOSX + lwz sp,0(sp) + else + addi sp,sp,64 + endif + lea r5,profile_globals + + and. r9,r3,r3 + beq init_profiler_error + + if USE_TEMPORARY_MEMORY + stw r9,Globals.profile_stack_handle(r5) + lwz r9,0(r9) + li r0,0 + stw r0,Globals.temp_handle_list(r5) + endif + if CHECK_STACK_OVERFLOWS + if 1 + lea r3,stack_size + lwz r3,0(r3) + else + li r3, (512*1024) % 65536 + addis r3,r3,(512*1024) / 65536 + endif + add r3,r3,r9 + stw r3,Globals.end_profile_stack(r5) + endif + lea r3,start_string + bl allocate_function_profile_record + + lwz r0,0(sp) + addi sp,sp,4 + mtlr r0 + + li r0,0 + stw r4,4(r9) + stw r0,0(r9) + addi r9,r9,8 + stw r9,Globals.stack_pointer(r5) + stw r0,Globals.last_tail_call(r5) + stw d7,Globals.n_words_free(r5) + + lwz r0,0(sp) + addi sp,sp,4 + +@store_clock: + time_hi r9 + stw r9,Globals.time_hi(r5) + time_lo r10 + time_hi r4 + stw r10,Globals.time_lo(r5) + cmpw 0,r4,r9 + beqlr+ + + b @store_clock + + if USE_TEMPORARY_MEMORY +allocate_temp_memory_handle: + mflr r0 + stw r31,-4(sp) + stw r0,8(sp) + stwu sp,-96(sp) + + addi r4,sp,56 + bl .TempNewHandle + nop + + mr. r31,r3 + beq return_r31 + + addi r4,sp,56 + bl .TempHLock + nop + + lha r0,56(sp) + cmpwi r0,0 + beq+ return_r31 + + mr r3,r31 + addi r4,sp,56 + bl .TempDisposeHandle + nop + + li r31,0 +return_r31: + lwz r0,104(sp) + mr r3,r31 + mtlr r0 + addi sp,sp,96 + lwz r31,-4(sp) + blr + +free_temp_memory_handle: + mflr r0 + stw r3,-4(sp) + stw r0,8(sp) + stwu sp,-96(sp) + + addi r4,sp,56 + bl .TempHUnlock + nop + + lwz r3,96-4(sp) + addi r4,sp,56 + bl .TempDisposeHandle + nop + + lwz r0,104(sp) + addi sp,sp,96 + mtlr r0 + blr + endif + +init_profiler_error1: + lea o0,wrong_processor + lea r5,profile_globals + li r4,0 + stw r4,Globals.stack_pointer(r5) + b print_error +init_profiler_error: + lea o0,not_enough_memory_for_profile_stack + lea r5,profile_globals + li r4,0 + stw r4,Globals.stack_pointer(r5) + b print_error +profiler_memory_error: + lea o0,not_enough_memory_for_profiler + b print_error + if CHECK_STACK_OVERFLOWS +profile_stack_overflow: + mflr r0 + stw r0,-4(sp) + stwu sp,-64(sp) + + bl .Debugger + nop + + lwz r0,64-4(sp) + addi sp,sp,64 + mtlr r0 + b profile_stack_overflow + endif + + + csect data{RW} +Globals: record +n_free_records_in_block:ds.l 1 ; 0 n free records in block +last_allocated_block: ds.l 1 ; 4 latest allocated block +profile_records: ds.l 1 ; 8 profile record list +time_hi: ds.l 1 ; 12 clock +time_lo: ds.l 1 +stack_pointer: ds.l 1 ; 20 stack pointer +last_tail_call ds.l 1 ; 24 last tail calling function +n_words_free: ds.l 1 + if USE_TEMPORARY_MEMORY +temp_handle_list ds.l 1 +profile_stack_handle ds.l 1 + endif + if CHECK_STACK_OVERFLOWS +end_profile_stack ds.l 1 + endif + endr + + align 2 +profile_globals: ds Globals + +profile_file_name: + dc.l __STRING__+2 + dc.l 0 + ds.b 32 + align 2 + if MODULE_NAMES +m_system: + dc.l 6 + dc.b 'System' + dc.b 0,0 + dc.l m_system + endif +start_string: + dc.l 0 + dc.b 'start' + dc.b 0 + align 2 +not_enough_memory_for_profile_stack: + dc.b 'not enough memory for profile stack' + dc.b 13 + dc.b 0 +not_enough_memory_for_profiler: + dc.b 'not enough memory for profiler' + dc.b 13 + dc.b 0 +wrong_processor: + if POWER601 + dc.b 'Not a PowerPC601 processor (don''t use profiling option for 601)' + else + dc.b 'This is a PowerPC601 processor (use profiling option for 601)' + endif + dc.b 13 + dc.b 0 +stack_trace_string: + dc.b 'Stack trace:' + dc.b 13 + dc.b 0 + align 2 + + macro + te &address + tc &address{TC},&address + endm + + toc + + te profile_globals + te profile_file_name + te not_enough_memory_for_profile_stack + te not_enough_memory_for_profiler + te wrong_processor + te start_string + te stack_trace_string + te new_file_creator + te stack_size |