# IBM_PROLOG_BEGIN_TAG # This is an automatically generated prolog. # # bos720 src/bos/usr/lib/kdb/MacroLib.perlmod 1.3 # # Licensed Materials - Property of IBM # # COPYRIGHT International Business Machines Corp. 1999,2001 # All Rights Reserved # # US Government Users Restricted Rights - Use, duplication or # disclosure restricted by GSA ADP Schedule Contract with IBM Corp. # # IBM_PROLOG_END_TAG ################################################################ package MacroLib; ################################################################ use init; ### import is required $main::{allcpu} = $main::MacroLib::{allcpu}; $main::{allthread} = $main::MacroLib::{allthread}; $main::{allpageins} = $main::MacroLib::{allpageins}; $main::{allstorage} = $main::MacroLib::{allstorage}; $main::{alllocks} = $main::MacroLib::{alllocks}; $main::{usemaster} = $main::MacroLib::{usemaster}; ############ # # usemaster # ############ sub usemaster { package Master; require "/usr/lib/kdb/masterscript.pm" or die "couldn't open masterscript.pm: $!"; master(@_); } ############ # # allcpu # ############ ### Displays the MST and the pending mpc services for each CPU. sub allcpu { print $Dump->stat; $ErrFound = undef; my $cpus = $Kernel->cpu_table; return unless ( defined $cpus ); return unless ( defined $cpus->count ); for ($index = 0; $index < $cpus->{count}; $index += 1) { $ErrFound = undef; print "\n*** CPU : $index ***\n"; my $cpu = $cpus->element($index); next unless ( defined $cpu ); $cpu->rawinfo =~ /(mpc_pend\W+\w+)\W/; next if ( defined $ErrFound ); print "\n$1\n"; next unless ( defined $cpu->mst_table ); print $cpu->mst_table->rawinfo; } } ############## # # allthread # ############## ### Displays the runnable threads , the thread table and the detailed ### report and stack of each thread which STATE is RUN or SLEEP. sub allthread { $ErrFound = undef; my $threads = $Kernel->thread_table; return unless ( defined $threads ); print "RUNNABLE THREADS :\n"; print "****************\n"; print $threads->running, "\n"; print "ALL THREADS\n"; print "***********\n"; print $threads->rawinfo, "\n"; return if ( defined $ErrFound ); print "Detailed listing\n"; print "****************\n"; return unless ( defined $threads->count ); for ($index = 0; $index < $threads->{count}; $index += 1) { $ErrFound = undef; my $thstate = $threads->tabfield2val($index, 'STATE'); if ( $thstate eq 'RUN' or $thstate eq 'SLEEP' ) { my $thread = $threads->element($index); next unless ( defined $thread ); print $thread->rawinfo,"\n"; next if ( defined $ErrFound ); my $stk = $thread->stack; next unless ( defined $stk ); next unless ( defined $stk->depth ); for ($index1 = 0; $index1 < $stk->{depth}; $index1 += 1) { print $stk->address($index1),"\t", $stk->routine($index1), "\t", $stk->offset($index1),"\n"; } } } } ############## # # allpageins # ############## ### Displays the table of threads waiting for PageIn. sub allpageins { $ErrFound = undef; my $threads = $Kernel->thread_table; return unless ( defined $threads ); print "THREADS WAITING FOR PAGING\n"; print "**************************\n"; print $threads->pageins, "\n"; } ############## # # allstorage # ############## ### Displays the VMM SCB Index , Segment ID , number of pgsp blocks and ### pages in real memory for each segment in use. sub allstorage { $ErrFound = undef; my $threads = $Kernel->thread_table; return unless ( defined $threads ); ### To sort the Segment Registers my @segtable = undef; my $tabindex = 0; my $indexed = sub { my $i; my $segt = shift; for ( $i=0; $i<$#segtable+1; $i++ ) { return 1 if ( $segt eq $segtable[$i] ); next; } return 0; }; ### DO NOT ERASE the ; return unless ( defined $threads->count ); for ( $index = 0; $index < $threads->{count}; $index += 1 ) { my $thstate = $threads->tabfield2val($index, 'STATE'); next unless ( $thstate eq 'RUN' or $thstate eq 'SLEEP' ); ### Threads which STATE is RUN or SLEEP my $thread = $threads->element($index); next unless ( defined $thread ); my $adspace = $thread->cur_space; next unless ( defined $adspace ); $adspace->rawinfo; next if ( defined $ErrFound ); for ($ind = 0; $ind <= 15; $ind += 1) { next unless ( $adspace->seginuse($ind) ); ### Each Segment Register in use $segtable[$tabindex++] = $adspace->segreg($ind) unless ( &$indexed( $adspace->segreg($ind) )); } } for ( $ind=0; $ind<$tabindex; $ind+=1 ) { my $segt = Segment->new( $segtable[$ind] ); next unless ( defined $segt ); $segt->rawinfo =~ /^(VMM SCB Addr.+)/m; next if ( defined $ErrFound ); print $1, "\n"; $segt->{rawinfo} =~ /^number of pgsp blocks\W+\w+\W+(\w+)/m; print "number of pgsp blocks : $1\n"; $segt->{rawinfo} =~ /^pages in real memory\W+\w+\W+(\w+)/m; print "pages in real memory : $1\n"; } } ############## # # alllocks # ############## ### Displays the detailed report and stack of the threads which hold a lock ### other threads are awaiting. sub alllocks { $ErrFound = undef; my $threads = $Kernel->thread_table; return unless ( defined $threads ); ### To sort the list of locks that threads are awaiting my @lcktable = undef; my $tabindex = 0; my $indexed = sub { my $i; my $lck = shift; for ( $i = 0; $i < $#lcktable+1; $i++ ) { return 1 if ( $lck eq $lcktable[$i] ); next; } return 0; }; ### DO NOT ERASE the ; return unless ( defined $threads->count ); for ( $index = 0; $index < $threads->{count}; $index += 1 ) { my $thstate = $threads->tabfield2val($index, 'STATE'); next unless ( $thstate eq 'RUN' or $thstate eq 'SLEEP' ); ### Threads which STATE is RUN or SLEEP my $thread = $threads->element($index); next unless ( defined $thread ); $thread->rawinfo =~ /wchan1\W+(\w+)\W+/; next if ( defined $ErrFound ); my $wchan1 = $1; next unless ( $1 =~ /[^0]+/ ); ### the thread is waiting for a lock $lcktable[$tabindex++] = $wchan1 unless &$indexed($wchan1); } ### Locks that threads are awaiting for ( $ind = 0; $ind < $tabindex; $ind += 1 ) { my $hold = $Memory->xbyte_view( $lcktable[$ind], 4 ); next if ( defined $ErrFound ); $hold =~ /:\W+\w+\W+(\w+)/m; # $Memory->xbyte_view( $lcktable[$ind], 4 ) =~ /:\W+\w+\W+(\w+)/m; my $tid = $1; for ( $i = 0; $i < $#tidtable + 1; $i++ ) { last if ( $1 eq $tidtable[$i] ); next; } ### This thread has not been listed yet if ( $i == $#tidtable + 1 ) { $tidtable[$i] = $1; my $thread = Thread->new; next unless ( defined $thread ); $thread->{_rawcmd} = [ ['senddata','ttid','signature'],['readdata'] ]; $thread->{signature} = $1; print $thread->rawinfo; next if ( defined $ErrFound ); my $stk = $thread->stack; next unless ( defined $stk ); print $stk->rawinfo; } } } ############## # # unimport # ############## ### Unload the functions of this library. sub unimport { for $key (keys %main::MacroLib::) { delete $main::MacroLib::{$key}; } for $key (keys %main::) { if ( $key =~ /MacroLib/ ) { delete $main::{$key}; } } for $key (keys %INC) { if ( $key =~ /MacroLib/ ) { delete $INC{$key}; } } for $key (keys %main::) { if ( $main::{$key} =~ /MacroLib/ ) { delete $main::{$key}; } } } 1;