// IfsTelnetDiskStat.bcpl -- IFS system statistics commands // Copyright Xerox Corporation 1979, 1980, 1981 // Last modified November 22, 1981 10:27 AM by Taft get "IfsDDMgr.decl" external [ // outgoing procedures DiskStatistics // incoming procedures Puts; Ws; PutTemplate; DoubleAdd; DoubleSubtract; Zero; Div32x16 LockDD; UnlockDD; ReadDDPage; Lock; Unlock // incoming statics dsp; driveTab; openLock ] //--------------------------------------------------------------------------- let DiskStatistics() be //--------------------------------------------------------------------------- [ Ws("*n*nDisk statistics (cumulative):") Ws("*nUn File system Transfers Err ECC Fix Rest Unrec BTerr Free") for drive = 0 to nDrives-1 do for fs = 0 to 1 do [ // Don't bother locking openLock here, because the worst possible effect // of having the disk disappear out from under us is that we print some // garbage numbers. let dte = lv driveTab>>DriveTab↑drive let disk = dte>>DTE.disk↑fs if disk ne 0 then [ PutTemplate(dsp, (dte>>DTE.disk↑1 eq 0? "*n$O ", "*n$O/$O "), drive, fs) let ifs = dte>>DTE.ifs test ifs ne 0 ifso [ Ws(ifs>>IFS.id) for i = 1 to 10-ifs>>IFS.id>>String.length do Puts(dsp, $*s) for u = 0 to nDisks-1 do if disk eq ifs>>IFS.lpdt↑u then PutTemplate(dsp, "($2O)", u) ] ifnot Ws("Not IFS ") PutTemplate(dsp, "$10ED$6ED$6ED$6ED$6ED$6ED$6ED$7UD", lv disk>>TFSDSK.nTransfers, lv disk>>TFSDSK.nErrors, lv disk>>TFSDSK.nECCErrors, lv disk>>TFSDSK.nECCFixes, lv disk>>TFSDSK.nRestores, lv disk>>TFSDSK.nUnRecov, lv disk>>TFSDSK.nBTErrors, disk>>TFSDSK.freePages) ] ] // DiskStatistics (cont'd) Ws("*n*nDisk drive statistics (since last restart):") Ws("*nUn Transfers Err ECC /10↑10 bits") for drive = 0 to nDrives-1 do [ let dte = lv driveTab>>DriveTab↑drive // Lock out changes to disk configuration -- needed because calling // ReadDDPage on a nonexistent disk would be disasterous. Lock(openLock) test dte>>DTE.ifs ne 0 ifso [ let nTransfers = vec 6; Zero(nTransfers, 6) let nErrors, nECCErrors = nTransfers+2, nTransfers+4 for fs = 0 to 1 do [ let disk = dte>>DTE.disk↑fs if disk ne 0 then [ let ddMgr = disk>>TFSDSK.ddMgr DoubleAdd(nTransfers, lv disk>>TFSDSK.nTransfers) DoubleAdd(nErrors, lv disk>>TFSDSK.nErrors) DoubleAdd(nECCErrors, lv disk>>TFSDSK.nECCErrors) LockDD(ddMgr, disk) let initialKD = lv (ReadDDPage(ddMgr, disk, 1))>>IFSKD.initialKD DoubleSubtract(nTransfers, lv initialKD>>TFSKD.nTransfers) DoubleSubtract(nErrors, lv initialKD>>TFSKD.nErrors) DoubleSubtract(nECCErrors, lv initialKD>>TFSKD.nECCErrors) UnlockDD(ddMgr, disk) ] ] Unlock(openLock) PutTemplate(dsp, "*n$O$11ED$6ED$6ED", drive, nTransfers, nErrors, nECCErrors) // To compute ECC errors per 10↑10 bits (T-300 spec): // rate = (nECCErrors * 10↑10)/(nTransfers * 2↑14) // where 2↑14 is the number of bits transferred per page. // 10↑10 is approximately equal to 2↑33, so we have: // rate = nECCErrors/(nTransfers * 2↑-(33-14)) = // nECCErrors/(nTransfers/2↑19) = (nECCErrors*2↑19)/nTransfers let rate = vec 1 rate!0, rate!1 = nECCErrors!1, 0 // God help us if more than 2↑16 errors Div32x16(nTransfers, 8) // to compute (nECCErrors*2↑16)/(nTransfers*2↑-3) while nTransfers!0 ne 0 do // double right shift the hard way [ Div32x16(rate, 2); Div32x16(nTransfers, 2) ] Div32x16(rate, nTransfers!1) // now denominator < 2↑16 PutTemplate(dsp, "$7ED", rate) ] ifnot Unlock(openLock) ] ]