# Function : add_resource
# ~~~~~~~~~~~~~~~~~~~~~~~
function add_resource (pblkres, newpid) {
if (index(pblkres, newpid))
return pblkres;
else
return pblkres " " newpid;
}
# Function : sameseq
# ~~~~~~~~~~~~~~~~~~
function sameseq(ev1, ev2, seq1, seq2) {
#printf("sameseq: Comparing :\n");
#printf("Ev=(%s) seq=(%s)\n", ev1, seq1);
#printf("against Ev=(%s) seq=(%s)\n", ev2, seq2);
if (!seq1) return 0;
if (seq1 != seq2) return 0;
if (ev1 != ev2) return 0;
if (ev1 ~ "'rdbms ipc message'" ||
ev1 ~ "'smon timer'"
||
ev1 ~ "'pmon timer'")
return 0;
return 1;
}
# Function : min
# ~~~~~~~~~~~~~~
function min(one, two) {
return (one }
# Function: procevent
# ~~~~~~~~~~~~~~~~~~~
function procevent (str) {
if (!eventdetail) return str;
realev = str;
sub("^.* for ", "", str);
sub("holding ", "", str);
sub("acquiring ", "", str);
#printf("DBG String = '%s'\n", str);
if (str == "'db file sequential read'"||str == "'db file scattered read'"
||
str == "'db file parallel write'" ||str == "'db file sequential write'" ||
str == "'buffer busy waits'" || str == "'free buffer waits'" ||
str == "'buffer deadlock'" || str == "'parallel query qref latch'")
{
getline; sub("
",""); gsub("="," ");
realev = realev " (" $2 $4 $6 ")";
}
else if (str == "'pipe get'")
{
getline; sub("
","");
realev = realev " (" $2 ")";
}
else if (str == "'parallel query dequeue wait'")
{
getline; sub("
","");
gsub("="," ");
realev = realev " (" $2 $4 $6 ")";
print_pqo = 1;
}
else if (str == "'enqueue'" || "'DFS lock acquisition'")
{
getline; sub("
",""); gsub("="," ");
# For now let's not do anything too clever !
if (substr($2, 1, 4) == "5351")
# SQ - sequence
realev = realev " (SQ(sequence) id=" $4 ")";
else if (substr($2, 1, 4) == "5356")
# SV - sequence
realev = realev " (SV(sequence) id=" $4 ")";
############################################
### The following tends to crowd the output.
############################################
#else
# realev = realev " (" $2 $4 $6 ")";
}
return realev;
}
# Function: pq_details
# ~~~~~~~~~~~~~~~~~~~~
function pq_details(rversion)
{
split(rversion, _ver, ".");
printf("\nAdditional Note:\n~~~~~~~~~~~~~~~~\n");
printf(" A 'parallel query dequeue' wait event has been encountered. The\n");
printf("arguments to this wait event are described below :\n\n");
if (_ver[2] < 2)
{
printf(" Parameter 1 - Process Queue to Dequeue\n");
}
else
{
#
Reasons can be seen in the fixed table X$KXFPSDS.
printf(" Parameter 1 - Reason for Dequeue. One of (Based upon 7.2.x) :\n");
printf("
0x01 - QC waiting for reply from Slaves for Parallel Recovery\n");
printf("
0x02 - Slave Dequeueing for Parallel Recovery\n");
printf("
0x03 - Waiting for the Join Group Message from new KXFP client\n");
printf("
0x04 - QC dequeueing from Slaves after starting a Server Group\n");
printf("
0x05 - Dequeueing a credit only\n");
printf("
0x06 - Dequeueing to free up a NULL buffer\n");
printf("
0x07 - Dequeueing to get the credit so that we can enqueue\n");
printf("
0x08 - Testing for dequeue\n");
printf("
0x09 - Slave is waiting to dequeue a message fragment from QC\n");
printf("
0x0a - QC waiting for Slaves to parse SQL and return OK\n");
printf("
0x0b - QC waiting to dequeue (execution reply) msg from slave\n");
printf("
0x0c - QC waiting to dequeue (execution) msg from slave\n");
printf("
0x0d - We are dequeueing a message (range partitioned)\n");
printf("
0x0e - We are dequeueing samples (consumer) from the QC\n");
printf("
0x0f - We are dequeueing a message (ordered)\n");
printf("
0x10 - Range TQ producer and are waiting to dequeue\n");
printf("
0x11 - Consumer waiting to dequeue prior to closing TQ\n");
}
printf(" Parameter 2 - Sleep Time/Sender Id\n");
printf("
Time to sleep in 1/100ths of a second\n");
printf("
If sleeptime greater than 0x10000000, the lower sixteen bits\n");
printf("
indicate the slave number on the remote instance indicated by\n");
printf("
the higher sixteen bits of the first 32 bits.\n");
printf(" Parameter 3 - Number of passes through the dequeueing code\n\n");
printf(" (This information assumes the trace file has a version number in the header)\n");
return 0;
}
# Function: pq_qc2slave
# ~~~~~~~~~~~~~~~~~~~~~
#
# Note: If the following line is added in then the awk script causes awk to
#
CORE dump under HP and AIX. The line is designed to make variables have
#
local scope but unfortunately it cannot be used here.
#function pq_qc2slave(state_no
,_tmp,_temp,_qcarr,_i,_j,_k,_qc,_slaveid)
function pq_qc2slave(state_no)
{
if (!(_qc = split(qclist[state_no], _qcarr, " ")))
return;
printf("\nQuery Co-Ordinator to Query Slave Mapping\n");
printf("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n");
## TODO: Add a Receiving/Sending message at end of line to denote what we are
##
up to.
#
o Make use of PS enqueues
(PS-instance-slave) (Output them in QC dump ?)
for (_i=1; _i<=_qc; _i++)
{
printf("QC=%5s
[Count=%s]\n", _qcarr[_i], qc_cnt[state_no, _qcarr[_i]]-1);
for (_j=0; _j
{
split(pqenq[_qcarr[_i], _j], _pqtmp, "-");
printf("%10s Communicates with Slave %d (hex) on instance %d (%s)\n",
" ",
_pqtmp[3], _pqtmp[2], pqenq[_qcarr[_i], _j]);
}
printf("%5s %8s %3s %8s %11s %11s %5s %7s %8s %4s\n",
"Slave", "Info", "Msg", "State", "From", "To",
"Type", "Status", "Mode","Err");
for (_j=qc_cnt[state_no, _qcarr[_i]]-1; _j0; _j--)
{
_temp = qc[state_no, _qcarr[_i], _j];
_slaveid = slave[state_no, _temp];
#printf("DBG: Slaveid = slave[sstate=%d, qref=%s]\n", state_no, _temp);
_printed = 0;
for (_k=0; _k<2; _k++)
{
_msg = pqdetail[state_no, _slaveid, _k];
if (!_msg) continue;
split(_msg, _tmp, " ");
printf("%5s %8s %3d %8s %11s %11s %5s %7s %8s %4s\n",
_printed?" ":_slaveid, pqenq[_slaveid, 0], _k, _tmp[1],
slave[state_no,_tmp[2]]?slave[state_no, _tmp[2]]:_tmp[2],
slave[state_no,_tmp[3]]?slave[state_no, _tmp[3]]:_tmp[3],
_tmp[4], _tmp[5], _tmp[6], _tmp[7]);
#printf("DBG: From = slave[sstate=%d, qref=%s]\n", state_no, _tmp[2]);
#printf("DBG: To
= slave[sstate=%d, qref=%s]\n", state_no, _tmp[3]);
_printed = 1;
}
}
}
printf("%*s------------------------\n", 25, " ");
printf("STATUS Key:\n");
printf("
DEQ = buffer has been dequeued\n");
printf("
EML = buffer on emergency message list\n");
printf("
ENQ = buffer has been enqueued\n");
printf("
FLST= buffer is on SGA freelist\n");
printf("
FRE = buffer is free (unused)\n");
printf("
GEB = buffer has been gotten for enqueuing\n");
printf("
GDB = dequeued buffer has been gotten \n");
printf("
INV = buffer is invalid (non-existent)\n");
printf("
QUE = buffer on queue message list\n");
printf("
RCV = buffer has been received \n");
printf("
NOFL= not on freelist (just removed)\n");
printf("%*s------------------------\n", 30, " ");
#
KXFPMTYINV
0 - Invalid message (new buffer).
[INV]
#
KXFPMTYNUL
1 - Null message, used to send credit.
[NUL]
#
KXFPMTYJOI
2 - Join group, from QC to slaves.
[JOI]
#
KXFPMTYERR
3 - Exiting group from slave to QC.
[ERR]
#
KXFPMTYRQS
4 - Request for statistics, QC to slaves. [RQS]
#
KXFPMTYSTA
5 - Statistics update, slaves to QC.
[STA]
#
KXFPMTYDTA
6 - User data, stuff kxfp doesn't look at.[DTA]
#
KXFPMTYJVR
7 - Slave to QC, ack and version number.
#
KXFPHSTRE :
0x01 - Stream mode, return credit immediately.
[STRE]
#
KXFPHDIAL :
0x02 - Dialog mode, expect a reply message.
[DIAL]
#
KXFPHNPNG :
0x04 - No pings, error if next message pings.
[NPNG]
#
KXFPMHPRI :
0x08 - Priority (JOIn|ERRor|EXIt) message.
[PRI]
#
KXFPMHSTP :
0x10 - Stream ping message. @@
[STP]
#
KXFPMHNDS :
0x20 - Non-default sized buffer.
[NDS]
#
KXFPMHCLR :
0x40 - Sent from a clear qref.
[CLR]
#
KXFPMHNID :
0x80 - No implicit dequeue.
[NID]
}