#include <cerrno>
#include <cstring>
#include <iostream>

#include <fcntl.h>
#include <sys/ioctl.h>
#include <unistd.h>

namespace {
constexpr unsigned ioctlMagic = 0xed;
constexpr unsigned getDriverVersion = _IOR(ioctlMagic, 15, unsigned int);

struct VersionInfo {
  unsigned major;
  unsigned minor;
  unsigned point;
};
} // namespace

int main(int argc, char **argv) {
  const char *device = argc > 1 ? argv[1] : "/dev/ipu0";
  const int fd = open(device, O_RDWR | O_CLOEXEC);
  if (fd < 0) {
    std::cerr << "open " << device << ": " << std::strerror(errno) << '\n';
    return 2;
  }
  VersionInfo version{};
  if (ioctl(fd, getDriverVersion, &version) != 0) {
    std::cerr << "IPU_GET_DRIVER_VERSION: " << std::strerror(errno) << '\n';
    close(fd);
    return 3;
  }
  close(fd);
  std::cout << "device=" << device << " driver=" << version.major << '.'
            << version.minor << '.' << version.point
            << " access=direct-kernel-abi PASS\n";
  return 0;
}
