Skip to content

Commit

Permalink
Merge branch 'develop' into ci_cdna_to_mi100
Browse files Browse the repository at this point in the history
  • Loading branch information
causten authored Sep 28, 2023
2 parents e7edd2e + cc50b9f commit a96ff08
Show file tree
Hide file tree
Showing 105 changed files with 1,231 additions and 1,093 deletions.
4 changes: 2 additions & 2 deletions docs/.sphinx/requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ charset-normalizer==3.1.0
# via requests
click==8.1.3
# via sphinx-external-toc
cryptography==41.0.3
cryptography==41.0.4
# via pyjwt
deprecated==1.2.13
# via pygithub
Expand Down Expand Up @@ -87,7 +87,7 @@ requests==2.28.2
# via
# pygithub
# sphinx
rocm-docs-core>=0.20.0
rocm-docs-core==0.24.2
# via -r requirements.in
smmap==5.0.0
# via gitdb
Expand Down
2 changes: 1 addition & 1 deletion docs/dev_intro.rst
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ In this case, we can create `argument <migraphx::argument>` objects directly fro
std::vector<float> results_vector(64);
result.visit([&](auto output) { results_vector.assign(output.begin(), output.end()); });

EXPECT(migraphx::verify::verify_range(results_vector, sol));
EXPECT(migraphx::verify::verify_rms_range(results_vector, sol));

An `argument <migraphx::argument>` can handle memory buffers from either the GPU or the CPU.
By default when running the `program <migraphx::program>`, buffers are allocated on the corresponding target.
Expand Down
12 changes: 10 additions & 2 deletions docs/driver.rst
Original file line number Diff line number Diff line change
Expand Up @@ -50,9 +50,17 @@ Runs reference and CPU or GPU implementations and checks outputs for consistency

.. include:: ./driver/compile.rst

.. option:: --tolerance [double]
.. option:: --rms-tol [double]

Tolerance for errors (Default: 80)
Tolerance for RMS error (Default: 0.001)

.. option:: --atol [double]

Tolerance for elementwise absolute difference (Default: 0.001)

.. option:: --rtol [double]

Tolerance for elementwise relative difference (Default: 0.001)

.. option:: -i, --per-instruction

Expand Down
4 changes: 3 additions & 1 deletion examples/migraphx/migraphx_driver/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,9 @@ See below for a comprehensive list of commands and option arguments, as well as
| --exhaustive-tune | Enable exhaustive search to find fastest kernel |
| --fp16 | Quantize for fp16 |
| --int8 | Quantize for int8 |
| --tolerance | Tolerance for errors |
| --rms-tol | Tolerance for the RMS error (Default: 0.001) |
| --atol | Tolerance for elementwise absolute difference (Default: 0.001) |
| --rtol | Tolerance for elementwise relative difference (Default: 0.001) |
| --per-instruction \| -i | Verify each instruction |
| --reduce \| -r | Reduce program and verify |
| --iterations \| -n | Number of iterations to run for perf report |
Expand Down
16 changes: 11 additions & 5 deletions src/driver/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -536,13 +536,19 @@ struct params : command<params>
struct verify : command<verify>
{
compiler c;
double tolerance = 80;
migraphx::verify::tolerance tols;
bool per_instruction = false;
bool reduce = false;
void parse(argument_parser& ap)
{
c.parse(ap);
ap(tolerance, {"--tolerance"}, ap.help("Tolerance for errors"));
ap(tols.rms_tol, {"--rms-tol"}, ap.help("Tolerance for the RMS error (Default: 0.001)"));
ap(tols.atol,
{"--atol"},
ap.help("Tolerance for the elementwise absolute difference (Default: 0.001)"));
ap(tols.rtol,
{"--rtol"},
ap.help("Tolerance for the elementwise relative difference (Default: 0.001)"));
ap(per_instruction,
{"-i", "--per-instruction"},
ap.help("Verify each instruction"),
Expand All @@ -567,15 +573,15 @@ struct verify : command<verify>

if(per_instruction)
{
verify_instructions(p, t, c.co, quantize, tolerance);
verify_instructions(p, t, c.co, quantize, tols);
}
else if(reduce)
{
verify_reduced_program(p, t, c.co, quantize, m, tolerance);
verify_reduced_program(p, t, c.co, quantize, m, tols);
}
else
{
verify_program(c.l.file, p, t, c.co, quantize, m, tolerance);
verify_program(c.l.file, p, t, c.co, quantize, m, tols);
}
}
};
Expand Down
31 changes: 15 additions & 16 deletions src/driver/verify.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -77,24 +77,24 @@ void verify_program(const std::string& name,
compile_options options,
precision quantize,
const parameter_map& inputs,
double tolerance)
verify::tolerance tols)
{
auto x = run_ref(p, inputs);
auto y = run_target(p, t, options, quantize, inputs);
auto ref_outs = run_ref(p, inputs);
auto target_outs = run_target(p, t, options, quantize, inputs);

std::size_t output_num = x.size();
std::size_t output_num = ref_outs.size();
for(std::size_t i = 0; i < output_num; ++i)
{
if(x[i].get_shape().type() != y[i].get_shape().type() or
x[i].get_shape().lens() != y[i].get_shape().lens())
if(ref_outs[i].get_shape().type() != target_outs[i].get_shape().type() or
ref_outs[i].get_shape().lens() != target_outs[i].get_shape().lens())
{
std::cout << "FAILED: " << name << std::endl;
std::cout << "Shape mismatch {" << x[i].get_shape() << "} != {" << y[i].get_shape()
<< "}" << std::endl;
std::cout << "Shape mismatch {" << ref_outs[i].get_shape() << "} != {"
<< target_outs[i].get_shape() << "}" << std::endl;
}
else
{
verify_args(name, x[i], y[i], tolerance);
verify_args(name, target_outs[i], verify::expected{ref_outs[i]}, tols);
}
}
}
Expand All @@ -103,7 +103,7 @@ void verify_instructions(const program& prog,
const target& t,
compile_options options,
precision quantize,
double tolerance)
verify::tolerance tols)
{
const auto* mm_prog = prog.get_main_module();
for(auto&& ins : (*mm_prog))
Expand Down Expand Up @@ -134,8 +134,7 @@ void verify_instructions(const program& prog,
{
std::cout << "Verify: " << ins.name() << std::endl;
std::cout << p << std::endl;
verify_program(
ins.name(), p, t, options, quantize, create_param_map(p, false), tolerance);
verify_program(ins.name(), p, t, options, quantize, create_param_map(p, false), tols);
}
catch(...)
{
Expand All @@ -151,7 +150,7 @@ void verify_reduced(program p,
compile_options options,
precision quantize,
const parameter_map& inputs,
double tolerance)
verify::tolerance tols)
{
auto* mm = p.get_main_module();
auto last = std::prev(mm->end(), n);
Expand All @@ -160,7 +159,7 @@ void verify_reduced(program p,
std::cout << p << std::endl;
try
{
verify_program(std::to_string(n), p, t, options, quantize, inputs, tolerance);
verify_program(std::to_string(n), p, t, options, quantize, inputs, tols);
}
catch(const std::exception& e)
{
Expand All @@ -174,7 +173,7 @@ void verify_reduced_program(const program& p,
compile_options options,
precision quantize,
const parameter_map& inputs,
double tolerance)
verify::tolerance tols)
{
const auto* mm = p.get_main_module();
auto n = std::distance(mm->begin(), mm->end());
Expand All @@ -187,7 +186,7 @@ void verify_reduced_program(const program& p,
std::cout << "Skip: " << i << std::endl;
continue;
}
verify_reduced(p, i, t, options, quantize, inputs, tolerance);
verify_reduced(p, i, t, options, quantize, inputs, tols);
}
}

Expand Down
7 changes: 4 additions & 3 deletions src/driver/verify.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@

#include "precision.hpp"
#include <migraphx/program.hpp>
#include <migraphx/verify.hpp>

namespace migraphx {
namespace driver {
Expand All @@ -37,18 +38,18 @@ void verify_program(const std::string& name,
compile_options options = compile_options{},
precision quantize = precision::fp32,
const parameter_map& inputs = {},
double tolerance = 100);
verify::tolerance tols = verify::tolerance{});
void verify_instructions(const program& prog,
const target& t,
compile_options options = compile_options{},
precision quantize = precision::fp32,
double tolerance = 80);
verify::tolerance tols = verify::tolerance{});
void verify_reduced_program(const program& p,
const target& t,
compile_options options = compile_options{},
precision quantize = precision::fp32,
const parameter_map& inputs = {},
double tolerance = 80);
verify::tolerance tols = verify::tolerance{});

} // namespace MIGRAPHX_INLINE_NS
} // namespace driver
Expand Down
98 changes: 94 additions & 4 deletions src/include/migraphx/verify.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -29,10 +29,13 @@
#include <functional>
#include <iostream>
#include <numeric>
#include <assert.h>

#include <migraphx/float_equal.hpp>
#include <migraphx/config.hpp>
#include <migraphx/env.hpp>

MIGRAPHX_DECLARE_ENV_VAR(MIGRAPHX_VERIFY_ENABLE_ALLCLOSE)
namespace migraphx {
inline namespace MIGRAPHX_INLINE_NS {
namespace verify {
Expand Down Expand Up @@ -187,16 +190,103 @@ double rms_range(const R1& r1, const R2& r2)
return std::numeric_limits<range_value<R1>>::max();
}

template <class R>
double get_rms_tol(const R&, std::size_t tolerance = 80)
{
double threshold = std::numeric_limits<range_value<R>>::epsilon() * tolerance;
return threshold;
}

/*
C++ doesn't support named arguments, this is just wrapper that helps distinguish between actual
results v/s expected results arguments.
*/
template <class T>
struct expected
{
expected() = default;
explicit expected(const T& input) : x(&input) {}
const T& data() const
{
assert(x != nullptr);
return *x;
}

private:
const T* x = nullptr;
};

// deduction guide for templated expected class
template <class T>
expected(const T&) -> expected<T>;

struct tolerance
{
double rms_tol = 0.001;
double atol = 0.001;
double rtol = 0.001;
};

/*
MIGraphX implementation of numpy's np.allclose() which checks if elementwise absolute diff is within
tolerance using this formula: abs(a - b) < atol + rtol(abs(b))
*/
template <class R1, class R2>
bool allclose(const R1& r1, const R2& r2, tolerance tols)
{
std::size_t n = range_distance(r1);
if(n == range_distance(r2))
{
auto idx = mismatch_idx(r1, r2, [&](auto x, auto y) {
return abs_diff(double(x), double(y)) < tols.atol + tols.rtol * std::abs(double(y));
});
return idx >= range_distance(r1);
}
return false;
}

template <class R1, class R2>
bool verify_range(const R1& r1, const R2& r2, double tolerance = 80, double* out_error = nullptr)
bool verify_rms_range(const R1& r1,
const R2& r2,
std::size_t tolerance = 80,
double* out_rms_error = nullptr)
{
double threshold = std::numeric_limits<range_value<R1>>::epsilon() * tolerance;
double threshold = get_rms_tol(r1, tolerance);
auto error = rms_range(r1, r2);
if(out_error != nullptr)
*out_error = error;
if(out_rms_error != nullptr)
*out_rms_error = error;
return error <= threshold;
}

template <class R1, class R2>
bool verify_range_with_tolerance(const R1& r1,
const expected<R2>& r2,
tolerance tols = tolerance{},
double* out_rms_error = nullptr)
{
auto rms_error = rms_range(r1, r2.data());
// disable ewise_verify by default for now, it requires lot of tests to be fixed
bool ewise_verify = true;
if(enabled(MIGRAPHX_VERIFY_ENABLE_ALLCLOSE{}))
{
ewise_verify = allclose(r1, r2.data(), tols);
}
if(out_rms_error != nullptr)
*out_rms_error = rms_error;
return rms_error <= tols.rms_tol and ewise_verify;
}

// expected argument should be passed as second, but if it is passed as the first by mistake then
// flip the order
template <class R1, class R2>
bool verify_range_with_tolerance(const expected<R1>& r1,
const R2& r2,
tolerance tols = tolerance{},
double* out_rms_error = nullptr)
{
return verify_rms_range(r2, r1, tols, out_rms_error);
}

} // namespace verify
} // namespace MIGRAPHX_INLINE_NS
} // namespace migraphx
Expand Down
14 changes: 9 additions & 5 deletions src/include/migraphx/verify_args.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,15 @@
namespace migraphx {
inline namespace MIGRAPHX_INLINE_NS {

MIGRAPHX_EXPORT
bool verify_args(const std::string& name,
const argument& ref_arg,
const argument& target_arg,
double tolerance = 80);
MIGRAPHX_EXPORT bool verify_args(const std::string& name,
const argument& target_arg,
const verify::expected<argument>& ref_arg,
verify::tolerance);

MIGRAPHX_EXPORT bool verify_args_with_tolerance(const std::string& name,
const argument& target_arg,
const verify::expected<argument>& ref_arg,
std::size_t tolerance = 80);

} // namespace MIGRAPHX_INLINE_NS
} // namespace migraphx
Expand Down
Loading

0 comments on commit a96ff08

Please sign in to comment.