1515bc8c1Sserge-sans-paille#!/usr/bin/env python 20928368fSKristof Beyls 30928368fSKristof Beyls# ULP error plot tool. 40928368fSKristof Beyls# 50928368fSKristof Beyls# Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 60928368fSKristof Beyls# See https://llvm.org/LICENSE.txt for license information. 70928368fSKristof Beyls# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 80928368fSKristof Beyls 90928368fSKristof Beylsimport numpy as np 100928368fSKristof Beylsimport matplotlib.pyplot as plt 110928368fSKristof Beylsimport sys 120928368fSKristof Beylsimport re 130928368fSKristof Beyls 140928368fSKristof Beyls# example usage: 150928368fSKristof Beyls# build/bin/ulp -e .0001 log 0.5 2.0 2345678 | math/tools/plot.py 160928368fSKristof Beyls 17*f98ee40fSTobias Hieta 180928368fSKristof Beylsdef fhex(s): 190928368fSKristof Beyls return float.fromhex(s) 200928368fSKristof Beyls 21*f98ee40fSTobias Hieta 220928368fSKristof Beylsdef parse(f): 230928368fSKristof Beyls xs = [] 240928368fSKristof Beyls gs = [] 250928368fSKristof Beyls ys = [] 260928368fSKristof Beyls es = [] 270928368fSKristof Beyls # Has to match the format used in ulp.c 28*f98ee40fSTobias Hieta r = re.compile(r"[^ (]+\(([^ )]*)\) got ([^ ]+) want ([^ ]+) [^ ]+ ulp err ([^ ]+)") 290928368fSKristof Beyls for line in f: 300928368fSKristof Beyls m = r.match(line) 310928368fSKristof Beyls if m: 320928368fSKristof Beyls x = fhex(m.group(1)) 330928368fSKristof Beyls g = fhex(m.group(2)) 340928368fSKristof Beyls y = fhex(m.group(3)) 350928368fSKristof Beyls e = float(m.group(4)) 360928368fSKristof Beyls xs.append(x) 370928368fSKristof Beyls gs.append(g) 380928368fSKristof Beyls ys.append(y) 390928368fSKristof Beyls es.append(e) 40*f98ee40fSTobias Hieta elif line.startswith("PASS") or line.startswith("FAIL"): 410928368fSKristof Beyls # Print the summary line 420928368fSKristof Beyls print(line) 430928368fSKristof Beyls return xs, gs, ys, es 440928368fSKristof Beyls 45*f98ee40fSTobias Hieta 460928368fSKristof Beylsdef plot(xs, gs, ys, es): 470928368fSKristof Beyls if len(xs) < 2: 48*f98ee40fSTobias Hieta print("not enough samples") 490928368fSKristof Beyls return 500928368fSKristof Beyls a = min(xs) 510928368fSKristof Beyls b = max(xs) 520928368fSKristof Beyls fig, (ax0, ax1) = plt.subplots(nrows=2) 530928368fSKristof Beyls es = np.abs(es) # ignore the sign 540928368fSKristof Beyls emax = max(es) 55*f98ee40fSTobias Hieta ax0.text(a + (b - a) * 0.7, emax * 0.8, "%s\n%g" % (emax.hex(), emax)) 56*f98ee40fSTobias Hieta ax0.plot(xs, es, "r.") 570928368fSKristof Beyls ax0.grid() 58*f98ee40fSTobias Hieta ax1.plot(xs, ys, "r.", label="want") 59*f98ee40fSTobias Hieta ax1.plot(xs, gs, "b.", label="got") 600928368fSKristof Beyls ax1.grid() 610928368fSKristof Beyls ax1.legend() 620928368fSKristof Beyls plt.show() 630928368fSKristof Beyls 64*f98ee40fSTobias Hieta 650928368fSKristof Beylsxs, gs, ys, es = parse(sys.stdin) 660928368fSKristof Beylsplot(xs, gs, ys, es) 67