Skip to content

Instantly share code, notes, and snippets.

@ninehills
Forked from drsnyder/urandom-reads.py
Created August 11, 2021 10:44
Show Gist options
  • Save ninehills/c16afe6fa48b4bdc1ee30617d99e7db2 to your computer and use it in GitHub Desktop.
Save ninehills/c16afe6fa48b4bdc1ee30617d99e7db2 to your computer and use it in GitHub Desktop.
Demonstrate the contention on /dev/urandom with N threads.
# Create a user land file for testing.
# dd if=/dev/urandom of=/tmp/urandom bs=1M count=10
#
# urandom-reads.py infile threads
# Examples:
# time python2.6 urandom-reads.py /tmp/urandom
# time python2.6 urandom-reads.py /dev/urandom
#
# R to generate a plot of the read time distribution at each level of concurrency
# rdt = read.csv("output.csv", header=F)
# rdt.n = rdt[complete.cases(rdt),]
# ggplot(rdt.n[rdt.n$threads<=16&rdt.n$time<0.1,], aes(x=threads,y=time, fill=as.factor(threads))) +
# geom_boxplot() + theme(legend.position="none") + scale_x_continuous(breaks=seq(1,16)) +
# labs(x="Threads", y="Time", title="/dev/urandom 4k Read Distributions")
import multiprocessing, sys, os, time
BYTES=4096
NUM_READS=1000
class UrandomReader(multiprocessing.Process):
def __init__(self, num_reads, num_bytes, infile, threads):
self.num_reads = num_reads
self.num_bytes = num_bytes
self.infile = infile
self.threads = threads
multiprocessing.Process.__init__(self)
def run(self):
fd = open(self.infile, 'rb')
for i in range(self.num_reads):
start = time.time()
b = fd.read(self.num_bytes)
assert(len(b) == self.num_bytes)
print "%d,%1.4f" % (threads, (time.time() - start))
if __name__ == '__main__':
if len(sys.argv) < 3:
print "%s <input-file> <threads>" % sys.argv[0]
sys.exit(1)
infile = sys.argv[1]
threads = int(sys.argv[2])
assert(threads > 0)
assert(os.path.exists(infile))
jobs = []
for i in range(threads):
p = UrandomReader(NUM_READS, BYTES, infile, threads)
jobs.append(p)
p.start()
for j in jobs:
j.join()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment