Hello.
2 monthes ago I talked in -current about new features for libdevstat.
Here is a new function, which calculate more statistics then 
existing compute_stats(). (compute_stats() calculate only average
results, not read/write results).
Please see my first step. Comments are welcome.
-- 

Rgdz,                                /"\ 
Sergey Osokin aka oZZ,               \ /  ASCII RIBBON CAMPAIGN
[EMAIL PROTECTED]                    X     AGAINST HTML MAIL
http://freebsd.org.ru/~osa/          / \
int
devstat_compute_statistics(struct devstat *current, struct devstat *previous,
                long double etime,
                u_int64_t *total_bytes,
                u_int64_t *total_bytes_read,
                u_int64_t *total_bytes_write,
                u_int64_t *total_transfers,
                u_int64_t *total_transfers_read,
                u_int64_t *total_transfers_write,
                u_int64_t *total_transfers_other,
                u_int64_t *total_blocks,
                u_int64_t *total_blocks_read,
                u_int64_t *total_blocks_write,
                long double *kb_per_transfer,
                long double *kb_per_transfer_read,
                long double *kb_per_transfer_write,
                long double *transfers_per_second,
                long double *transfers_per_second_read,
                long double *transfers_per_second_write,
                long double *transfers_per_second_other,
                long double *mb_per_second,
                long double *mb_per_second_read,
                long double *mb_per_second_write,
                long double *blocks_per_second,
                long double *blocks_per_second_read,
                long double *blocks_per_second_write,
                long double *ms_per_transaction,
                long double *ms_per_transaction_read,
                long double *ms_per_transaction_write)
                
{
        u_int64_t totalbytes, totalbytes_read, totalbytes_write;
        u_int64_t totaltransfers, totaltransfers_read, totaltransfers_write, 
totaltransfers_other;
        u_int64_t totalblocks, totalblocks_read, totalblocks_write;
        char *func_name = "devstat_compute_statistics";

        /*
         * current is the only mandatory field.
         */
        if (current == NULL) {
                sprintf(devstat_errbuf, "%s: current stats structure was NULL",
                        func_name);
                return(-1);
        }
/*
        totalbytes = (current->bytes_written + current->bytes_read) -
                ((previous) ? (previous->bytes_written +
                        previous->bytes_read) : 0);

        if (total_bytes)
                *total_bytes = totalbytes;
*/

        totalbytes_read = current->bytes_read - ((previous) ? previous->bytes_read) : 
0);

        if (total_bytes_read)
                *total_bytes_read = totalbytes_read;

        totalbytes_write = current->bytes_written - ((previous) ? 
(previous->bytes_written) : 0);

        if (total_bytes_write)
                *total_bytes_write = totalbytes_write;

        totalbytes = totalbytes_read + totalbytes_write;

        if (total_bytes)
                *total_bytes = totalbytes;

/*
        totaltransfers = (current->num_reads +
                          current->num_writes +
                          current->num_other) -
                        ((previous) ?
                         (previous->num_reads +
                          previous->num_writes +
                          previous->num_other) : 0);

        if (total_transfers)
                *total_transfers = totaltransfers;
*/

        totaltransfers_read = current->num_reads - ((previous) ? (previous->num_reads) 
: 0);

        if (total_transfers_read)
                *total_transfers_read = totaltransfers_read;

        totaltransfers_write = current->num_writes - ((previous) ? 
(previous->num_writes) : 0);

        if (total_transfers_write)
                *total_transfers_write = totaltransfers_write;

        totaltransfers_other = current->num_other - ((previous) ? 
(previous->num_other) : 0);

        if (total_transfers_other)
                *total_transfers_other = totaltransfers_other;

        totaltransfers = totaltransfers_read + totaltransfers_write + 
totaltransfers_other;

        if (total_transfers)
                *total_transfers = totaltransfers;

        if (transfers_per_second) {
                if (etime > 0.0) {
                        *transfers_per_second = totaltransfers;
                        *transfers_per_second /= etime;
                } else
                        *transfers_per_second = 0.0;
        }

        if (transfers_per_second_read) {
                if (etime > 0.0) {
                        *transfers_per_second_read = totaltransfers_read;
                        *transfers_per_second_read /= etime;
                } else
                        *transfers_per_second_read = 0.0;
        }

        if (transfers_per_second_write) {
                if (etime > 0.0) {
                        *transfers_per_second_write = totaltransfers_write;
                        *transfers_per_second_write /= etime;
                } else
                        *transfers_per_second_write = 0.0;
        }

        if (transfers_per_second_other) {
                if (etime > 0.0) {
                        *transfers_per_second_other = totaltransfers_other;
                        *transfers_per_second_other /= etime;
                } else
                        *transfers_per_second_other = 0.0;
        }

        if (kb_per_transfer) {
                *kb_per_transfer = totalbytes;
                *kb_per_transfer /= 1024;
                if (totaltransfers > 0)
                        *kb_per_transfer /= totaltransfers;
                else
                        *kb_per_transfer = 0.0;
        }


        if (kb_per_transfer_read) {
                *kb_per_transfer_read = totalbytes_read;
                *kb_per_transfer_read /= 1024;
                if (totaltransfers_read > 0)
                        *kb_per_transfer_read /= totaltransfers_read;
                else
                        *kb_per_transfer_read = 0.0;
        }


        if (kb_per_transfer_write) {
                *kb_per_transfer_write = totalbytes_write;
                *kb_per_transfer_write /= 1024;
                if (totaltransfers_write > 0)
                        *kb_per_transfer_write /= totaltransfers_write;
                else
                        *kb_per_transfer_write = 0.0;
        }

        if (mb_per_second) {
                *mb_per_second = totalbytes;
                *mb_per_second /= 1024 * 1024;
                if (etime > 0.0)
                        *mb_per_second /= etime;
                else
                        *mb_per_second = 0.0;
        }

        if (mb_per_second_read) {
                *mb_per_second_read = totalbytes_read;
                *mb_per_second_read /= 1024 * 1024;
                if (etime > 0.0)
                        *mb_per_second_read /= etime;
                else
                        *mb_per_second_read = 0.0;
        }

        if (mb_per_second_write) {
                *mb_per_second_write = totalbytes_write;
                *mb_per_second_write /= 1024 * 1024;
                if (etime > 0.0)
                        *mb_per_second_write /= etime;
                else
                        *mb_per_second_write = 0.0;
        }

        totalblocks = totalbytes;
        totalblocks_read = totalbytes_read;
        totalblocks_write = totalbytes_write;

        if (current->block_size > 0) {
                totalblocks /= current->block_size;
                totalblocks_read /= current->block_size;
                totalblocks_write /= current->block_size;
        }
        else {
                totalblocks /= 512;
                totalblocks_read /= 512;
                totalblocks_write /= 512;
        }

        if (total_blocks)
                *total_blocks = totalblocks;

        if (total_blocks_read)
                *total_blocks_read = totalblocks_read;

        if (total_blocks_write)
                *total_blocks_write = totalblocks_write;

        if (blocks_per_second) {
                *blocks_per_second = totalblocks;
                if (etime > 0.0)
                        *blocks_per_second /= etime;
                else
                        *blocks_per_second = 0.0;
        }

        if (blocks_per_second_read) {
                *blocks_per_second_read = totalblocks_read;
                if (etime > 0.0)
                        *blocks_per_second_read /= etime;
                else
                        *blocks_per_second_read = 0.0;
        }

        if (blocks_per_second_write) {
                *blocks_per_second_write = totalblocks_write;
                if (etime > 0.0)
                        *blocks_per_second_write /= etime;
                else
                        *blocks_per_second_write = 0.0;
        }

        if (ms_per_transaction) {
                if (totaltransfers > 0) {
                        *ms_per_transaction = etime;
                        *ms_per_transaction /= totaltransfers;
                        *ms_per_transaction *= 1000;
                } else
                        *ms_per_transaction = 0.0;
        }

        if (ms_per_transaction_read) {
                if (totaltransfers_read > 0) {
                        *ms_per_transaction_read = etime;
                        *ms_per_transaction_read /= totaltransfers_read;
                        *ms_per_transaction_read *= 1000;
                } else
                        *ms_per_transaction_read = 0.0;
        }

        if (ms_per_transaction_write) {
                if (totaltransfers_write > 0) {
                        *ms_per_transaction_write = etime;
                        *ms_per_transaction_write /= totaltransfers_write;
                        *ms_per_transaction_write *= 1000;
                } else
                        *ms_per_transaction_write = 0.0;
        }

        return(0);
}

Reply via email to