// Copyright(c) 2017-2018, Intel Corporation // // Redistribution and use in source and binary forms, with or without // modification, are permitted provided that the following conditions are met: // // * Redistributions of source code must retain the above copyright notice, // this list of conditions and the following disclaimer. // * Redistributions in binary form must reproduce the above copyright notice, // this list of conditions and the following disclaimer in the documentation // and/or other materials provided with the distribution. // * Neither the name of Intel Corporation nor the names of its contributors // may be used to endorse or promote products derived from this software // without specific prior written permission. // // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE // POSSIBILITY OF SUCH DAMAGE. #include #include #include #include #include #include #include "mock/test_system.h" #include "platform/fpga_hw.h" namespace py = pybind11; using namespace opae::testing; PYBIND11_EMBEDDED_MODULE(mopae, m) { m.doc() = "Open Programmable Acceleration Engine"; } PYBIND11_EMBEDDED_MODULE(mockopae, m) { py::class_ pytp(m, "test_platform"); pytp.def_static("platforms", &test_platform::platforms) .def_static("get", &test_platform::get) .def_static("exists", &test_platform::exists) .def("is_mock", [](test_platform &p) { return p.mock_sysfs != nullptr; }) .def_property_readonly("devices", [](test_platform &p) { return p.devices; }); ; py::class_ pytd(m, "test_device"); pytd.def_property_readonly("afu_guid", [](test_device &td) { return td.afu_guid; }) .def_property_readonly("fme_guid", [](test_device &td) { return td.fme_guid; }); py::class_ pyts(m, "test_system"); pyts.def(py::init(&test_system::instance)) .def("initialize", &test_system::initialize) .def("finalize", &test_system::finalize) .def("prepare_sysfs", &test_system::prepare_syfs) .def("remove_sysfs", &test_system::remove_sysfs); } int run_unittest(const char *testpy, py::module pymain) { auto globals = py::globals(); auto mock = py::module::import("mockopae"); auto unit = py::module::import("unittest"); auto scope = py::dict(pymain.attr("__dict__")); globals["mockopae"] = mock; globals["unittest"] = unit; try { py::eval_file(testpy, scope); auto suite = unit.attr("TestLoader")().attr("loadTestsFromModule")(pymain); py::dict kwargs; kwargs["verbosity"] = 2; auto runner = unit.attr("TextTestRunner")(**kwargs); auto result = runner.attr("run")(suite); return result.attr("wasSuccessful")().cast() ? 0 : 1; } catch (py::error_already_set &ex) { test_system::instance()->finalize(); std::cerr << "error executing: " << testpy << " - " << ex.what() << "\n"; ex.restore(); } return EXIT_FAILURE; } int main(int argc, char *argv[]) { py::scoped_interpreter guard{}; auto locals = py::dict(); auto globals = py::globals(); auto mopae = py::module::import("mopae"); auto _opae = py::module::import("_opae"); mopae.attr("fpga") = _opae; globals["opae"] = mopae; if (argc > 1) { auto pymain = py::module::import("__main__"); if (argc > 2 && std::string(argv[1]) == "test") { return run_unittest(argv[2], pymain); } py::list pyargv; auto sys = py::module::import("sys"); for (int i = 1; i < argc; ++i) { pyargv.append(argv[i]); } sys.attr("argv") = pyargv; try { py::eval_file(argv[1], pymain.attr("__dict__")); } catch (py::error_already_set &pyerr) { if (!pyerr.matches(PyExc_SystemExit)) { pyerr.restore(); } } } return 0; }