# DO NOT MODIFY: this is automatically generated by the ctypes-wrapper

import os
import ctypes as ct

def catch_errors(f):
    def wrapper(*args):
        errcode = ct.c_int(0)
        errmsg = ct.c_char_p(0)
        output = f(*args, ct.byref(errcode), ct.byref(errmsg))
        if errcode.value != 0:
            msg = errmsg.value.decode('ascii')
            lib.free_error_message(errmsg)
            raise RuntimeError(msg)
        return output
    return wrapper

# TODO: surely there's a better way than whatever this is.
dirname = os.path.dirname(os.path.abspath(__file__))
contents = os.listdir(dirname)
lib = None
for x in contents:
    if x.startswith('core') and not x.endswith("py"):
        lib = ct.CDLL(os.path.join(dirname, x))
        break

if lib is None:
    raise ImportError("failed to find the core.* module")

lib.free_error_message.argtypes = [ ct.POINTER(ct.c_char_p) ]

lib.py_extract_column.argtypes = [
    ct.c_void_p,
    ct.c_int,
    ct.c_void_p,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

lib.py_extract_ncol.restype = ct.c_int
lib.py_extract_ncol.argtypes = [
    ct.c_void_p,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

lib.py_extract_nrow.restype = ct.c_int
lib.py_extract_nrow.argtypes = [
    ct.c_void_p,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

lib.py_extract_row.argtypes = [
    ct.c_void_p,
    ct.c_int,
    ct.c_void_p,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

lib.py_extract_sparse.restype = ct.c_int
lib.py_extract_sparse.argtypes = [
    ct.c_void_p,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

lib.py_free_mat.argtypes = [
    ct.c_void_p,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

lib.py_initialize_compressed_sparse_matrix.restype = ct.c_void_p
lib.py_initialize_compressed_sparse_matrix.argtypes = [
    ct.c_int,
    ct.c_int,
    ct.c_uint64,
    ct.c_void_p,
    ct.c_void_p,
    ct.c_void_p,
    ct.c_void_p,
    ct.c_void_p,
    ct.c_uint8,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

lib.py_initialize_dense_matrix.restype = ct.c_void_p
lib.py_initialize_dense_matrix.argtypes = [
    ct.c_int,
    ct.c_int,
    ct.c_void_p,
    ct.c_void_p,
    ct.c_uint8,
    ct.POINTER(ct.c_int),
    ct.POINTER(ct.c_char_p)
]

def extract_column(rawmat, c, output):
    return catch_errors(lib.py_extract_column)(rawmat, c, output)

def extract_ncol(mat):
    return catch_errors(lib.py_extract_ncol)(mat)

def extract_nrow(mat):
    return catch_errors(lib.py_extract_nrow)(mat)

def extract_row(rawmat, r, output):
    return catch_errors(lib.py_extract_row)(rawmat, r, output)

def extract_sparse(mat):
    return catch_errors(lib.py_extract_sparse)(mat)

def free_mat(mat):
    return catch_errors(lib.py_free_mat)(mat)

def initialize_compressed_sparse_matrix(nr, nc, nz, dtype, dptr, itype, iptr, indptr, byrow):
    return catch_errors(lib.py_initialize_compressed_sparse_matrix)(nr, nc, nz, dtype, dptr, itype, iptr, indptr, byrow)

def initialize_dense_matrix(nr, nc, type, ptr, byrow):
    return catch_errors(lib.py_initialize_dense_matrix)(nr, nc, type, ptr, byrow)