#!/usr/bin/perl # Usage: # ./chewmem.pl # Description: # This will create a character array requiring "MiB" actual memory. # Summarize high-level memory usage. # Ideally we can demonstate creating larger and larger # successful memory allocations until Avail is near 0. # It is very likely to trigger OOM Killer or cause reset # if we run completely out of memory. use warnings; use strict; use POSIX qw(strftime); sub show_memusage() { our $count; $::count++; $::count %= 15; my $Ki = 1024.0; my ($MemTotal, $MemFree, $Buffers, $Cached, $CommitLimit, $Committed_AS, $Slab, $SReclaimable); # Process all entries of MEMINFO my $file = '/proc/meminfo'; open(FILE, $file) || die "Cannot open file: $file ($!)"; MEMINFO_LOOP: while($_ = ) { s/[\0\e\f\r\a]//g; chomp; # strip control characters if any last MEMINFO_LOOP if (/^\s*$/); # end at blank-line if (/\bMemTotal:\s+(\d+)\s+kB/) { $MemTotal = $1; next MEMINFO_LOOP; } if (/\bMemFree:\s+(\d+)\s+kB/) { $MemFree = $1; next MEMINFO_LOOP; } if (/\bBuffers:\s+(\d+)\s+kB/) { $Buffers = $1; next MEMINFO_LOOP; } if (/\bCached:\s+(\d+)\s+kB/) { $Cached = $1; next MEMINFO_LOOP; } if (/\bCommitLimit:\s+(\d+)\s+kB/) { $CommitLimit = $1; next MEMINFO_LOOP; } if (/\bCommitted_AS:\s+(\d+)\s+kB/) { $Committed_AS = $1; next MEMINFO_LOOP; } if (/\bSlab:\s+(\d+)\s+kB/) { $Slab = $1; next MEMINFO_LOOP; } if (/\bSReclaimable:\s+(\d+)\s+kB/) { $SReclaimable = $1; next MEMINFO_LOOP; } } close(FILE); my $Avail_MiB = ($MemFree + $Cached + $Buffers + $SReclaimable)/$Ki; my $Strict_MiB = ($CommitLimit - $Committed_AS)/$Ki; my $now = strftime "%Y-%m-%d %H:%M:%S", localtime(); if ($::count == 1) { printf "%19s %6s %6s %6s %6s %6s %6s %6s %6s %6s\n", 'yyyy-mm-dd hh:mm:ss', 'Tot', 'Free', 'Ca', 'Buf', 'Slab', 'CAS', 'CLim', 'Avail', 'Strict'; } printf "%19s %6.1f %6.1f %6.1f %6.1f %6.1f %6.1f %6.1f %6.1f %6.1f\n", $now, $MemTotal/$Ki, $MemFree/$Ki, $Cached/$Ki, $Buffers/$Ki, $Slab/$Ki, $Committed_AS/$Ki, $CommitLimit/$Ki, $Avail_MiB, $Strict_MiB; } #------------------------------------------------------------------------------- # MAIN PROGRAM # Autoflush output select(STDERR); $| = 1; select(STDOUT); # default $| = 1; my $MiB = $ARGV[0] ||=0.0; my $A = "A" x (1024*1024*$MiB/2); print "Allocating $MiB MiB character array.\n"; while(1) { sleep(1); show_memusage(); } exit 0; 1;