From d7fc669bf0dbe37f46d2efec4940feb8504017c2 Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Thu, 11 Feb 2016 14:24:01 +0100 Subject: Change no_set_check parameter name. Move Python wrap to separate directory. --- pywrap/CMakeLists.txt | 22 ++ pywrap/pcipywrap.c | 542 ++++++++++++++++++++++++++++++++++++++++++++++++++ pywrap/pcipywrap.i | 21 ++ pywrap/server.py | 184 +++++++++++++++++ 4 files changed, 769 insertions(+) create mode 100644 pywrap/CMakeLists.txt create mode 100644 pywrap/pcipywrap.c create mode 100644 pywrap/pcipywrap.i create mode 100644 pywrap/server.py (limited to 'pywrap') diff --git a/pywrap/CMakeLists.txt b/pywrap/CMakeLists.txt new file mode 100644 index 0000000..e5f7ea7 --- /dev/null +++ b/pywrap/CMakeLists.txt @@ -0,0 +1,22 @@ +include_directories( + ${CMAKE_SOURCE_DIR} + ${CMAKE_BINARY_DIR} + ${CMAKE_SOURCE_DIR}/pcilib + ${CMAKE_BINARY_DIR}/pcilib + ${LIBXML2_INCLUDE_DIRS} + ${PYTHON_INCLUDE_DIR} + ${UTHASH_INCLUDE_DIRS} +) + +#Creating python wrapping +INCLUDE(${SWIG_USE_FILE}) + +INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}) + +SET(CMAKE_SWIG_FLAGS "") + +SET_SOURCE_FILES_PROPERTIES(pcipywrap.i PROPERTIES SWIG_FLAGS "-includeall") +SWIG_ADD_MODULE(pcipywrap python pcipywrap.i pcipywrap.c) +SWIG_LINK_LIBRARIES(pcipywrap ${PYTHON_LIBRARIES} pcilib) + +configure_file(server.py server.py) diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c new file mode 100644 index 0000000..c5164a8 --- /dev/null +++ b/pywrap/pcipywrap.c @@ -0,0 +1,542 @@ +#include "pci.h" +#include "error.h" +#include + +/*! + * \brief Global pointer to pcilib_t context. + * Used by setPcilib and read_register. + */ +pcilib_t* __ctx = 0; + +/*! + * \brief Wraping for vsnprintf function, that saves string to char* + * \return saved from vsnprintf string + */ +char* vmake_str(const char* msg, va_list vl) +{ + char *buf; + size_t sz; + + va_list vl_copy; + va_copy(vl_copy, vl); + + sz = vsnprintf(NULL, 0, msg, vl); + buf = (char *)malloc(sz + 1); + + if(!buf) + { + return NULL; + } + + vsnprintf(buf, sz+1, msg, vl_copy); + va_end(vl_copy); + + return buf; +} + +/*! + * \brief Wraping for vsnprintf function, that saves string to char* + * \return saved from vsnprintf string + */ +char* make_str(const char* msg, ...) +{ + va_list vl; + va_start(vl, msg); + char *buf = vmake_str(msg, vl); + va_end(vl); + return buf; +} + +/*! + * \brief Version of pcilib_logger_t, that saves error text to Python exeption + */ +void pcilib_print_error_to_py(void *arg, const char *file, int line, + pcilib_log_priority_t prio, const char *msg, + va_list va) { + char* buf_raw_msg = vmake_str(msg, va); + char* buf_wrapped_message = make_str("%s [%s:%d]\n", buf_raw_msg, file, line); + + printf("%s", buf_wrapped_message); + PyErr_SetString(PyExc_Exception, buf_wrapped_message); + + free(buf_wrapped_message); + free(buf_raw_msg); +} + +/*! + * \brief Inits pcipywrap module at importing + */ +void init_pcipywrap_module() +{ + pcilib_set_logger(pcilib_get_logger_min_prio(), + pcilib_print_error_to_py, + pcilib_get_logger_argument()); +} + +/*! + * \brief Wraps for pcilib_open function. + * \param[in] fpga_device path to the device file [/dev/fpga0] + * \param[in] model specifies the model of hardware, autodetected if NULL is passed + * \return Pointer to pcilib_t, created by pcilib_open, serialized to bytearray; NULL with exeption text, if failed. + */ +PyObject* createPcilibInstance(const char *fpga_device, const char *model) +{ + //opening device + pcilib_t* ctx = pcilib_open(fpga_device, model); + if(!ctx) + return NULL; + + //serializing object + return PyByteArray_FromStringAndSize((const char*)&ctx, sizeof(pcilib_t*)); +} + +/*! + * \brief Closes current pciliv instance, if its open. + */ +void closeCurrentPcilibInstance() +{ + if(__ctx) + { + pcilib_close(__ctx); + __ctx = NULL; + } +} + +/*! + * \brief Returns current opened pcilib_t instatnce + * \return Pointer to pcilib_t, serialized to bytearray + */ +PyObject* getCurrentPcilibInstance() +{ + return PyByteArray_FromStringAndSize((const char*)&__ctx, sizeof(pcilib_t*)); +} + +/*! + * \brief Sets pcilib context to wraper. + * \param[in] addr Pointer to pcilib_t, serialized to bytearray + * \return 1, serialized to PyObject or NULL with exeption text, if failed. + */ +PyObject* setPcilib(PyObject* addr) +{ + if(!PyByteArray_Check(addr)) + { + pcilib_error("Incorrect addr type. Only bytearray is allowed"); + return NULL; + } + + //deserializing adress + char* pAddr = PyByteArray_AsString(addr); + + //hard copy context adress + for(int i = 0; i < sizeof(pcilib_t*) + 10; i++) + ((char*)&__ctx)[i] = pAddr[i]; + + return PyInt_FromLong((long)1); +} + + +/*! + * \brief Reads register value. Wrap for pcilib_read_register function. + * \param[in] regname the name of the register + * \param[in] bank should specify the bank name if register with the same name may occur in multiple banks, NULL otherwise + * \return register value, can be integer or float type; NULL with exeption text, if failed. + */ +PyObject* read_register(const char *regname, const char *bank) +{ + if(!__ctx) + { + pcilib_error("pcilib_t handler not initialized"); + return NULL; + } + + pcilib_value_t val = {0}; + pcilib_register_value_t reg_value; + + int err; + + err = pcilib_read_register(__ctx, bank, regname, ®_value); + if(err) + { + pcilib_error("Failed: pcilib_read_register (%i)", err); + return NULL; + } + + err = pcilib_set_value_from_register_value(__ctx, &val, reg_value); + if(err) + { + pcilib_error("Failed: pcilib_set_value_from_register_value (%i)", err); + return NULL; + } + + return pcilib_convert_val_to_pyobject(__ctx, &val); +} + +/*! + * \brief Writes value to register. Wrap for pcilib_write_register function. + * \param[in] val Register value, that needs to be set. Can be int, float or string. + * \param[in] regname the name of the register + * \param[in] bank should specify the bank name if register with the same name may occur in multiple banks, NULL otherwise + * \return 1, serialized to PyObject or NULL with exeption text, if failed. + */ +PyObject* write_register(PyObject* val, const char *regname, const char *bank) +{ + if(!__ctx) + { + pcilib_error("pcilib_t handler not initialized"); + return NULL; + } + + pcilib_value_t val_internal = {0}; + pcilib_register_value_t reg_value; + + int err; + err = pcilib_convert_pyobject_to_val(__ctx, val, &val_internal); + if(err) + { + pcilib_error("Failed pcilib_convert_pyobject_to_val (%i)", err); + return NULL; + } + + reg_value = pcilib_get_value_as_register_value(__ctx, &val_internal, &err); + if(err) + { + pcilib_error("Failed: pcilib_get_value_as_register_value (%i)", err); + return NULL; + } + + err = pcilib_write_register(__ctx, bank, regname, reg_value); + if(err) + { + pcilib_error("Failed: pcilib_write_register (%i)", err); + return NULL; + } + return PyInt_FromLong((long)1); +} + +/*! + * \brief Reads propety value. Wrap for pcilib_get_property function. + * \param[in] prop property name (full name including path) + * \return property value, can be integer or float type; NULL with exeption text, if failed. + */ +PyObject* get_property(const char *prop) +{ + if(!__ctx) + { + pcilib_error("pcilib_t handler not initialized"); + return NULL; + } + + int err; + pcilib_value_t val = {0}; + + err = pcilib_get_property(__ctx, prop, &val); + + if(err) + { + pcilib_error("Failed pcilib_get_property (%i)", err); + return NULL; + } + + return pcilib_convert_val_to_pyobject(__ctx, &val); +} + +/*! + * \brief Writes value to property. Wrap for pcilib_set_property function. + * \param[in] prop property name (full name including path) + * \param[in] val Property value, that needs to be set. Can be int, float or string. + * \return 1, serialized to PyObject or NULL with exeption text, if failed. + */ +PyObject* set_property(const char *prop, PyObject* val) +{ + int err; + + if(!__ctx) + { + pcilib_error("pcilib_t handler not initialized"); + return NULL; + } + + pcilib_value_t val_internal = {0}; + err = pcilib_convert_pyobject_to_val(__ctx, val, &val_internal); + if(err) + { + pcilib_error("Failed pcilib_convert_pyobject_to_val (%i)", err); + return NULL; + } + + err = pcilib_set_property(__ctx, prop, &val_internal); + + if(err) + { + pcilib_error("Failed pcilib_get_property (%i)", err); + return NULL; + } + + return PyInt_FromLong((long)1); +} + +void add_pcilib_value_to_dict(PyObject* dict, pcilib_value_t* val, const char *name) +{ + PyObject *py_val = (PyObject*)pcilib_convert_val_to_pyobject(__ctx, val); + + if(py_val) + PyDict_SetItem(dict, + PyString_FromString(name), + py_val); + else + PyDict_SetItem(dict, + PyString_FromString("defvalue"), + PyString_FromString("invalid")); +} + +PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listItem) +{ + PyObject* pylistItem = PyDict_New(); + + if(listItem.name) + PyDict_SetItem(pylistItem, + PyString_FromString("name"), + PyString_FromString(listItem.name)); + + if(listItem.description) + PyDict_SetItem(pylistItem, + PyString_FromString("description"), + PyString_FromString(listItem.description)); + + if(listItem.path) + PyDict_SetItem(pylistItem, + PyString_FromString("path"), + PyString_FromString(listItem.path)); + + //serialize types + const char* type = "invalid"; + switch(listItem.type) + { + case PCILIB_TYPE_INVALID: + type = "invalid"; + break; + case PCILIB_TYPE_STRING: + type = "string"; + break; + case PCILIB_TYPE_DOUBLE: + type = "double"; + break; + case PCILIB_TYPE_LONG : + type = "long"; + break; + default: + break; + } + PyDict_SetItem(pylistItem, + PyString_FromString("type"), + PyString_FromString(type)); + + + //serialize modes + PyObject* modes = PyList_New(0); + + if((listItem.mode & PCILIB_ACCESS_R ) == PCILIB_REGISTER_R) + PyList_Append(modes, PyString_FromString("R")); + if((listItem.mode & PCILIB_ACCESS_W ) == PCILIB_REGISTER_W) + PyList_Append(modes, PyString_FromString("W")); + if((listItem.mode & PCILIB_ACCESS_RW ) == PCILIB_REGISTER_RW) + PyList_Append(modes, PyString_FromString("RW")); + if((listItem.mode & PCILIB_REGISTER_INCONSISTENT) == PCILIB_REGISTER_INCONSISTENT) + PyList_Append(modes, PyString_FromString("NO_CHK")); + + PyDict_SetItem(pylistItem, + PyString_FromString("mode"), + modes); + + //serialize flags + PyObject* flags = PyList_New(0); + + if((listItem.flags & PCILIB_LIST_FLAG_CHILDS ) == PCILIB_LIST_FLAG_CHILDS) + PyList_Append(flags, PyString_FromString("childs")); + + PyDict_SetItem(pylistItem, + PyString_FromString("flags"), + flags); + + if(listItem.unit) + PyDict_SetItem(pylistItem, + PyString_FromString("unit"), + PyString_FromString(listItem.unit)); + + return pylistItem; +} + +PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listItem) +{ + PyObject* pylistItem = PyDict_New(); + + if(listItem.name) + PyDict_SetItem(pylistItem, + PyString_FromString("name"), + PyString_FromString(listItem.name)); + + if(listItem.description) + PyDict_SetItem(pylistItem, + PyString_FromString("description"), + PyString_FromString(listItem.description)); + + if(listItem.bank) + PyDict_SetItem(pylistItem, + PyString_FromString("bank"), + PyString_FromString(listItem.bank)); + + //serialize modes + PyObject* modes = PyList_New(0); + + if((listItem.mode & PCILIB_REGISTER_R) == PCILIB_REGISTER_R) + PyList_Append(modes, PyString_FromString("R")); + if((listItem.mode & PCILIB_REGISTER_W) == PCILIB_REGISTER_W) + PyList_Append(modes, PyString_FromString("W")); + if((listItem.mode & PCILIB_REGISTER_RW) == PCILIB_REGISTER_RW) + PyList_Append(modes, PyString_FromString("RW")); + if((listItem.mode & PCILIB_REGISTER_W1C) == PCILIB_REGISTER_W1C) + PyList_Append(modes, PyString_FromString("W1C")); + if((listItem.mode & PCILIB_REGISTER_RW1C) == PCILIB_REGISTER_RW1C) + PyList_Append(modes, PyString_FromString("RW1C")); + if((listItem.mode & PCILIB_REGISTER_W1I) == PCILIB_REGISTER_W1I) + PyList_Append(modes, PyString_FromString("W1I")); + if((listItem.mode & PCILIB_REGISTER_RW1I) == PCILIB_REGISTER_RW1I) + PyList_Append(modes, PyString_FromString("RW1I")); + if((listItem.mode & PCILIB_REGISTER_INCONSISTENT) == PCILIB_REGISTER_INCONSISTENT) + PyList_Append(modes, PyString_FromString("NO_CHK")); + + PyDict_SetItem(pylistItem, + PyString_FromString("mode"), + modes); + + pcilib_value_t defval = {0}; + pcilib_set_value_from_register_value(__ctx, &defval, listItem.defvalue); + add_pcilib_value_to_dict(pylistItem, &defval, "defvalue"); + + if(listItem.range) + { + pcilib_value_t minval = {0}; + pcilib_set_value_from_register_value(__ctx, &minval, listItem.range->min); + + pcilib_value_t maxval = {0}; + pcilib_set_value_from_register_value(__ctx, &maxval, listItem.range->max); + + PyObject* range = PyDict_New(); + add_pcilib_value_to_dict(range, &minval, "min"); + add_pcilib_value_to_dict(range, &maxval, "max"); + PyDict_SetItem(pylistItem, + PyString_FromString("range"), + range); + } + + if(listItem.values) + { + PyObject* values = PyList_New(0); + + for (int j = 0; listItem.values[j].name; j++) + { + PyObject* valuesItem = PyDict_New(); + + pcilib_value_t val = {0}; + pcilib_set_value_from_register_value(__ctx, &val, listItem.values[j].value); + + pcilib_value_t min = {0}; + pcilib_set_value_from_register_value(__ctx, &min, listItem.values[j].min); + + pcilib_value_t max = {0}; + pcilib_set_value_from_register_value(__ctx, &max, listItem.values[j].max); + + add_pcilib_value_to_dict(valuesItem, &val, "value"); + add_pcilib_value_to_dict(valuesItem, &min, "min"); + add_pcilib_value_to_dict(valuesItem, &max, "max"); + + if(listItem.values[j].name) + PyDict_SetItem(valuesItem, + PyString_FromString("name"), + PyString_FromString(listItem.values[j].name)); + + if(listItem.values[j].description) + PyDict_SetItem(valuesItem, + PyString_FromString("name"), + PyString_FromString(listItem.values[j].description)); + + PyList_Append(values, valuesItem); + } + + PyDict_SetItem(pylistItem, + PyString_FromString("values"), + values); + } + + return pylistItem; +} + +PyObject* get_registers_list(const char *bank) +{ + if(!__ctx) + { + pcilib_error("pcilib_t handler not initialized"); + return NULL; + } + + pcilib_register_info_t *list = pcilib_get_register_list(__ctx, bank, PCILIB_LIST_FLAGS_DEFAULT); + + PyObject* pyList = PyList_New(0); + for(int i = 0; i < __ctx->num_reg; i++) + { + //serialize item attributes + PyObject* pylistItem = pcilib_convert_register_info_to_pyobject(list[i]); + PyList_Append(pyList, pylistItem); + } + + pcilib_free_register_info(__ctx, list); + + return pyList; +} + +PyObject* get_register_info(const char* reg,const char *bank) +{ + if(!__ctx) + { + pcilib_error("pcilib_t handler not initialized"); + return NULL; + } + + pcilib_register_info_t *info = pcilib_get_register_info(__ctx, bank, reg, PCILIB_LIST_FLAGS_DEFAULT); + + if(!info) + { + pcilib_error("Failed pcilib_get_register_info"); + return NULL; + } + + PyObject* py_info = pcilib_convert_register_info_to_pyobject(info[0]); + + pcilib_free_register_info(__ctx, info); + + return py_info; +} + +PyObject* get_property_info(const char* branch) +{ + if(!__ctx) + { + pcilib_error("pcilib_t handler not initialized"); + return NULL; + } + + pcilib_property_info_t *list = pcilib_get_property_list(__ctx, branch, PCILIB_LIST_FLAGS_DEFAULT); + + PyObject* pyList = PyList_New(0); + + for(int i = 0; list[i].path; i++) + { + //serialize item attributes + PyObject* pylistItem = pcilib_convert_property_info_to_pyobject(list[i]); + PyList_Append(pyList, pylistItem); + } + + pcilib_free_property_info(__ctx, list); + + return pyList; +} diff --git a/pywrap/pcipywrap.i b/pywrap/pcipywrap.i new file mode 100644 index 0000000..3ff23a9 --- /dev/null +++ b/pywrap/pcipywrap.i @@ -0,0 +1,21 @@ +%module pcipywrap + +%init %{ + init_pcipywrap_module(); +%} + +extern PyObject* createPcilibInstance(const char *fpga_device, const char *model = NULL); +extern PyObject* setPcilib(PyObject* addr); +extern void closeCurrentPcilibInstance(); +extern PyObject* getCurrentPcilibInstance(); + +extern PyObject* read_register(const char *regname, const char *bank = NULL); +extern PyObject* write_register(PyObject* val, const char *regname, const char *bank = NULL); + +extern PyObject* get_property(const char *prop); +extern PyObject* set_property(const char *prop, PyObject* val); + +extern PyObject* get_registers_list(const char *bank = NULL); +extern PyObject* get_register_info(const char* reg,const char *bank = NULL); + +extern PyObject* get_property_info(const char* branch = NULL); diff --git a/pywrap/server.py b/pywrap/server.py new file mode 100644 index 0000000..d308867 --- /dev/null +++ b/pywrap/server.py @@ -0,0 +1,184 @@ +import time +import os #delete later +import pcipywrap +import json +import BaseHTTPServer + +class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): + + def do_HEAD(s): + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + + def do_GET(s): + length = int(s.headers['Content-Length']) + + #deserialize input data + data = json.loads(s.rfile.read(length).decode('utf-8')) + + if 'command' in data: + command = data['command'] + if(command == 'help'): + s.help(data) + + elif(command == 'open'): + #check required arguments + if not 'device' in data: + s.error('message doesnt contains "device" field, ' + 'which is required for "open" command', data) + return + #parse command arguments and convert them to string + device = str(data.get('device', None)) + model = data.get('model', None) + if not model is None: + model = str(model) + + try: + s.openPcilibInstance(device, model) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + s.wrapMessageAndSend(out, data) + + elif(command == 'get_registers_list'): + #parse command arguments and convert them to string + bank = data.get('bank', None) + if not bank is None: + bank = str(bank) + + registers = dict() + try: + registers = pcipywrap.get_registers_list(bank) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + out['registers'] = registers + s.wrapMessageAndSend(out, data) + + elif(command == 'get_register_info'): + #check required arguments + if not 'reg' in data: + s.error('message doesnt contains "reg" field, ' + 'which is required for "get_register_info" command', data) + return + + #parse command arguments and convert them to string + reg = str(data.get('reg', None)) + bank = data.get('bank', None) + if not bank is None: + bank = str(bank) + + register = dict() + try: + register = pcipywrap.get_register_info(reg, bank) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + out['register'] = register + s.wrapMessageAndSend(out, data) + + elif(command == 'get_property_info'): + #parse command arguments and convert them to string + branch = data.get('branch', None) + if not branch is None: + branch = str(bank) + + properties = dict() + try: + properties = pcipywrap.get_property_info(branch) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + out['properties'] = properties + s.wrapMessageAndSend(out, data) + + else: + s.error('command "' + command + '" undefined', data) + return + else: + s.error('message doesnt contains "command" field, which is required', data) + return + + + #print str(s.headers['content-type']) + #print post_data['some'] + + """open device context """ + def openPcilibInstance(s, device, model): + pcipywrap.closeCurrentPcilibInstance() + + lib = pcipywrap.createPcilibInstance(device, model) + pcipywrap.setPcilib(lib) + + """Send help message""" + def help(s, received_message = None): + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = {'status': 'ok', 'help' : 'under construction'} + s.wrapMessageAndSend(out, received_message) + + """Send error message with text description""" + def error(s, info, received_message = None): + s.send_response(400) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + + out['status'] = 'error' + out['description'] = info + out['note'] = 'send {"command" : "help"} to get help' + s.wrapMessageAndSend(out, received_message) + + def wrapMessageAndSend(s, message, received_message = None): + if not received_message is None: + message['received_message'] = received_message + s.wfile.write(json.dumps(message)) + +HOST_NAME = '' # !!!REMEMBER TO CHANGE THIS!!! +PORT_NUMBER = 12412 # Maybe set this to 9000. + +if __name__ == '__main__': + #initialize variables test (to remove) + os.environ["APP_PATH"] = '/home/vchernov/1215N/pcitool' + os.environ["PCILIB_MODEL_DIR"] = os.environ["APP_PATH"] + "/xml" + os.environ["LD_LIBRARY_PATH"] = os.environ["APP_PATH"] + "/pcilib" + + pcilib_server = BaseHTTPServer.HTTPServer + httpd = pcilib_server((HOST_NAME, PORT_NUMBER), PcilibServerHandler) + print time.asctime(), "Server Starts - %s:%s" % (HOST_NAME, PORT_NUMBER) + try: + httpd.serve_forever() + except KeyboardInterrupt: + pass + httpd.server_close() + print time.asctime(), "Server Stops - %s:%s" % (HOST_NAME, PORT_NUMBER) -- cgit v1.2.3 From 55eab7196d0104c71e40136b3b22e9501d234e17 Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Fri, 12 Feb 2016 14:43:20 +0100 Subject: 1. Cmakelists - move copy xml folder command to root file 2. - Move set python paths code to python module init funtction - pci.c move python module init block code after checking model to get paths before it runs. - Fix set python path code to work with PYTHONPATH - Update pci run script to work with PYTHONPATH - Fix python finalize code 3. Change pcilib_script_s interacting method. Now it stores in hash. 4. Change names of some fucntions to more unified ones 5. Remove old unused function pcilib_xml_create_script_or_transform_view 6. cli - disable reading register after set if write_verification flag is off 7. Remove uninformative error messages fro Python wrap. 8. - Server.py - add read/write property/register command handling - Add help message - Correcting paths --- pywrap/pcipywrap.c | 50 +++--------- pywrap/pcipywrap.i | 10 +-- pywrap/server.py | 230 +++++++++++++++++++++++++++++++++++++++++++++++++---- 3 files changed, 233 insertions(+), 57 deletions(-) (limited to 'pywrap') diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index c5164a8..fc0add1 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -4,7 +4,7 @@ /*! * \brief Global pointer to pcilib_t context. - * Used by setPcilib and read_register. + * Used by set_pcilib and read_register. */ pcilib_t* __ctx = 0; @@ -68,6 +68,7 @@ void pcilib_print_error_to_py(void *arg, const char *file, int line, */ void init_pcipywrap_module() { + printf("init_pcipywrap_module\n"); pcilib_set_logger(pcilib_get_logger_min_prio(), pcilib_print_error_to_py, pcilib_get_logger_argument()); @@ -79,7 +80,7 @@ void init_pcipywrap_module() * \param[in] model specifies the model of hardware, autodetected if NULL is passed * \return Pointer to pcilib_t, created by pcilib_open, serialized to bytearray; NULL with exeption text, if failed. */ -PyObject* createPcilibInstance(const char *fpga_device, const char *model) +PyObject* create_pcilib_instance(const char *fpga_device, const char *model) { //opening device pcilib_t* ctx = pcilib_open(fpga_device, model); @@ -93,7 +94,7 @@ PyObject* createPcilibInstance(const char *fpga_device, const char *model) /*! * \brief Closes current pciliv instance, if its open. */ -void closeCurrentPcilibInstance() +void close_curr_pcilib_instance() { if(__ctx) { @@ -106,7 +107,7 @@ void closeCurrentPcilibInstance() * \brief Returns current opened pcilib_t instatnce * \return Pointer to pcilib_t, serialized to bytearray */ -PyObject* getCurrentPcilibInstance() +PyObject* get_curr_pcilib_instance() { return PyByteArray_FromStringAndSize((const char*)&__ctx, sizeof(pcilib_t*)); } @@ -116,7 +117,7 @@ PyObject* getCurrentPcilibInstance() * \param[in] addr Pointer to pcilib_t, serialized to bytearray * \return 1, serialized to PyObject or NULL with exeption text, if failed. */ -PyObject* setPcilib(PyObject* addr) +PyObject* set_pcilib(PyObject* addr) { if(!PyByteArray_Check(addr)) { @@ -156,19 +157,13 @@ PyObject* read_register(const char *regname, const char *bank) err = pcilib_read_register(__ctx, bank, regname, ®_value); if(err) - { - pcilib_error("Failed: pcilib_read_register (%i)", err); return NULL; - } err = pcilib_set_value_from_register_value(__ctx, &val, reg_value); if(err) - { - pcilib_error("Failed: pcilib_set_value_from_register_value (%i)", err); return NULL; - } - return pcilib_convert_val_to_pyobject(__ctx, &val); + return pcilib_get_value_as_pyobject(__ctx, &val); } /*! @@ -190,26 +185,17 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) pcilib_register_value_t reg_value; int err; - err = pcilib_convert_pyobject_to_val(__ctx, val, &val_internal); + err = pcilib_set_value_from_pyobject(__ctx, val, &val_internal); if(err) - { - pcilib_error("Failed pcilib_convert_pyobject_to_val (%i)", err); return NULL; - } reg_value = pcilib_get_value_as_register_value(__ctx, &val_internal, &err); if(err) - { - pcilib_error("Failed: pcilib_get_value_as_register_value (%i)", err); return NULL; - } err = pcilib_write_register(__ctx, bank, regname, reg_value); if(err) - { - pcilib_error("Failed: pcilib_write_register (%i)", err); return NULL; - } return PyInt_FromLong((long)1); } @@ -232,12 +218,9 @@ PyObject* get_property(const char *prop) err = pcilib_get_property(__ctx, prop, &val); if(err) - { - pcilib_error("Failed pcilib_get_property (%i)", err); - return NULL; - } + return NULL; - return pcilib_convert_val_to_pyobject(__ctx, &val); + return pcilib_get_value_as_pyobject(__ctx, &val); } /*! @@ -246,7 +229,7 @@ PyObject* get_property(const char *prop) * \param[in] val Property value, that needs to be set. Can be int, float or string. * \return 1, serialized to PyObject or NULL with exeption text, if failed. */ -PyObject* set_property(const char *prop, PyObject* val) +PyObject* set_property(PyObject* val, const char *prop) { int err; @@ -257,27 +240,21 @@ PyObject* set_property(const char *prop, PyObject* val) } pcilib_value_t val_internal = {0}; - err = pcilib_convert_pyobject_to_val(__ctx, val, &val_internal); + err = pcilib_set_value_from_pyobject(__ctx, val, &val_internal); if(err) - { - pcilib_error("Failed pcilib_convert_pyobject_to_val (%i)", err); return NULL; - } err = pcilib_set_property(__ctx, prop, &val_internal); if(err) - { - pcilib_error("Failed pcilib_get_property (%i)", err); return NULL; - } return PyInt_FromLong((long)1); } void add_pcilib_value_to_dict(PyObject* dict, pcilib_value_t* val, const char *name) { - PyObject *py_val = (PyObject*)pcilib_convert_val_to_pyobject(__ctx, val); + PyObject *py_val = (PyObject*)pcilib_get_value_as_pyobject(__ctx, val); if(py_val) PyDict_SetItem(dict, @@ -506,7 +483,6 @@ PyObject* get_register_info(const char* reg,const char *bank) if(!info) { - pcilib_error("Failed pcilib_get_register_info"); return NULL; } diff --git a/pywrap/pcipywrap.i b/pywrap/pcipywrap.i index 3ff23a9..95045f3 100644 --- a/pywrap/pcipywrap.i +++ b/pywrap/pcipywrap.i @@ -4,16 +4,16 @@ init_pcipywrap_module(); %} -extern PyObject* createPcilibInstance(const char *fpga_device, const char *model = NULL); -extern PyObject* setPcilib(PyObject* addr); -extern void closeCurrentPcilibInstance(); -extern PyObject* getCurrentPcilibInstance(); +extern PyObject* create_pcilib_instance(const char *fpga_device, const char *model = NULL); +extern PyObject* set_pcilib(PyObject* addr); +extern void close_curr_pcilib_instance(); +extern PyObject* get_curr_pcilib_instance(); extern PyObject* read_register(const char *regname, const char *bank = NULL); extern PyObject* write_register(PyObject* val, const char *regname, const char *bank = NULL); extern PyObject* get_property(const char *prop); -extern PyObject* set_property(const char *prop, PyObject* val); +extern PyObject* set_property(PyObject* val, const char *prop); extern PyObject* get_registers_list(const char *bank = NULL); extern PyObject* get_register_info(const char* reg,const char *bank = NULL); diff --git a/pywrap/server.py b/pywrap/server.py index d308867..0da6bc8 100644 --- a/pywrap/server.py +++ b/pywrap/server.py @@ -1,8 +1,10 @@ import time -import os #delete later +import os import pcipywrap import json import BaseHTTPServer +import sys +import getopt class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): @@ -70,8 +72,8 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): out['registers'] = registers s.wrapMessageAndSend(out, data) - elif(command == 'get_register_info'): - #check required arguments + elif(command == 'get_register_info'): + #check required arguments if not 'reg' in data: s.error('message doesnt contains "reg" field, ' 'which is required for "get_register_info" command', data) @@ -81,7 +83,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): reg = str(data.get('reg', None)) bank = data.get('bank', None) if not bank is None: - bank = str(bank) + bank = str(bank) register = dict() try: @@ -120,6 +122,125 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): out['status'] = 'ok' out['properties'] = properties s.wrapMessageAndSend(out, data) + + elif(command == 'read_register'): + #check required arguments + if not 'reg' in data: + s.error('message doesnt contains "reg" field, ' + 'which is required for "read_register" command', data) + return + + #parse command arguments and convert them to string + reg = str(data.get('reg', None)) + bank = data.get('bank', None) + if not bank is None: + bank = str(bank) + + value = 0 + try: + value = pcipywrap.read_register(reg, bank) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + out['value'] = value + s.wrapMessageAndSend(out, data) + + elif(command == 'write_register'): + #check required arguments + if not 'reg' in data: + s.error('message doesnt contains "reg" field, ' + 'which is required for "write_register" command', data) + return + + if not 'value' in data: + s.error('message doesnt contains "value" field, ' + 'which is required for "write_register" command', data) + return + + #parse command arguments and convert them to string + reg = str(data.get('reg', None)) + value = str(data.get('value', None)) + bank = data.get('bank', None) + if not bank is None: + bank = str(bank) + + try: + pcipywrap.write_register(value, reg, bank) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + s.wrapMessageAndSend(out, data) + + elif(command == 'get_property'): + #check required arguments + if not 'prop' in data: + s.error('message doesnt contains "prop" field, ' + 'which is required for "get_property" command', data) + return + + #parse command arguments and convert them to string + prop = str(data.get('prop', None)) + + value = 0 + try: + value = pcipywrap.get_property(prop) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + out['value'] = value + s.wrapMessageAndSend(out, data) + + elif(command == 'set_property'): + #check required arguments + if not 'prop' in data: + s.error('message doesnt contains "prop" field, ' + 'which is required for "set_property" command', data) + return + + if not 'value' in data: + s.error('message doesnt contains "value" field, ' + 'which is required for "set_property" command', data) + return + + #parse command arguments and convert them to string + prop = str(data.get('prop', None)) + value = str(data.get('value', None)) + + try: + pcipywrap.set_property(value, prop) + except Exception as e: + s.error(str(e), data) + return + + #Success! Create and send reply + s.send_response(200) + s.send_header('content-type', 'application/json') + s.end_headers() + out = dict() + out['status'] = 'ok' + s.wrapMessageAndSend(out, data) + else: s.error('command "' + command + '" undefined', data) @@ -134,19 +255,78 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): """open device context """ def openPcilibInstance(s, device, model): - pcipywrap.closeCurrentPcilibInstance() + pcipywrap.close_curr_pcilib_instance() - lib = pcipywrap.createPcilibInstance(device, model) - pcipywrap.setPcilib(lib) + lib = pcipywrap.create_pcilib_instance(device, model) + pcipywrap.set_pcilib(lib) """Send help message""" def help(s, received_message = None): s.send_response(200) s.send_header('content-type', 'application/json') s.end_headers() - out = {'status': 'ok', 'help' : 'under construction'} + usage = str('Usage:\n' + ' Server receive commands via http GET with json packet.\n' + ' content-type should have value "application/json"\n' + ' Server could handle only commands. to set command, you\n' + ' should specify field "command" in packet with command name\n' + ' List of commands:\n' + '\n' + ' command: help - Get help. This will return usage\n' + '\n' + + ' command: open - Opens context of device. It will be reopened if already open.\n' + ' required fields\n' + ' device: - path to the device file [/dev/fpga0]\n' + ' optional fields\n' + ' model: - specifies the model of hardware, autodetected if doesnt exists\n' + '\n' + + ' command: get_registers_list - Returns the list of registers provided by the hardware model.\n' + ' optional fields\n' + ' bank: - if set, only register within the specified bank will be returned\n' + '\n' + + ' command: get_register_info - Returns the information about the specified register.\n' + ' required fields\n' + ' reg: - the name of the register\n' + ' optional fields\n' + ' bank: - if set, only register within the specified bank will be returned\n' + '\n' + + ' command: get_property_info - Returns the list of properties available under the specified path.\n' + ' optional fields\n' + ' branch: - Path. If not set, will return the top-level properties\n' + '\n' + + ' command: read_register - Reads the specified register.\n' + ' required fields\n' + ' reg: - the name of the register\n' + ' optional fields\n' + ' bank: - if set, only register within the specified bank will be processed\n' + '\n' + + ' command: write_register - Writes to specified register.\n' + ' required fields\n' + ' reg: - the name of the register\n' + ' value: - the register value to write. Should be int, float or string (with number)\n' + ' optional fields\n' + ' bank: - if set, only register within the specified bank will be processed\n' + '\n' + + ' command: get_property - Reads / computes the property value.\n' + ' required fields\n' + ' prop: - full name including path\n' + '\n' + + ' command: set_property - Writes the property value or executes the code associated with property.\n' + ' required fields\n' + ' prop: - full name including path\n' + ' value: - the property value to write. Should be int, float or string (with number)\n' + '\n') + out = {'status': 'ok', 'usage' : usage} s.wrapMessageAndSend(out, received_message) - + """Send error message with text description""" def error(s, info, received_message = None): s.send_response(400) @@ -164,14 +344,34 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): message['received_message'] = received_message s.wfile.write(json.dumps(message)) -HOST_NAME = '' # !!!REMEMBER TO CHANGE THIS!!! -PORT_NUMBER = 12412 # Maybe set this to 9000. if __name__ == '__main__': - #initialize variables test (to remove) - os.environ["APP_PATH"] = '/home/vchernov/1215N/pcitool' - os.environ["PCILIB_MODEL_DIR"] = os.environ["APP_PATH"] + "/xml" - os.environ["LD_LIBRARY_PATH"] = os.environ["APP_PATH"] + "/pcilib" + + HOST_NAME = '' # !!!REMEMBER TO CHANGE THIS!!! + PORT_NUMBER = 12412 # Maybe set this to 9000. + + try: + opts, args = getopt.getopt(sys.argv[1:], "", []) + #opts, args = getopt.getopt(sys.argv[1:], "hop:v", ["help", "output="]) + #print opts, args + except getopt.GetoptError as err: + # print help information and exit: + print str(err) # will print something like "option -a not recognized" + #usage() + sys.exit(2) + + #Set enviroment variables, if it not setted already + if not 'APP_PATH' in os.environ: + APP_PATH = '' + file_dir = os.path.dirname(os.path.abspath(__file__)) + APP_PATH = str(os.path.abspath(file_dir + '/../..')) + os.environ["APP_PATH"] = APP_PATH + + if not 'PCILIB_MODEL_DIR' in os.environ: + os.environ['PCILIB_MODEL_DIR'] = os.environ["APP_PATH"] + "/xml" + + if not 'LD_LIBRARY_PATH' in os.environ: + os.environ['LD_LIBRARY_PATH'] = os.environ["APP_PATH"] + "/pcilib" pcilib_server = BaseHTTPServer.HTTPServer httpd = pcilib_server((HOST_NAME, PORT_NUMBER), PcilibServerHandler) -- cgit v1.2.3 From 1b3342649294c6ce99aeb82664a29eac47687ee5 Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Fri, 12 Feb 2016 17:50:57 +0100 Subject: Move python module init code to transfom view constructor Update python logger and python exeption messages Change serialization method in create_pcilib_instance set_pcilib functions --- pywrap/pcipywrap.c | 110 ++++++++++++++++++++++++++++++++++++++--------------- pywrap/pcipywrap.i | 4 +- pywrap/server.py | 3 ++ 3 files changed, 84 insertions(+), 33 deletions(-) (limited to 'pywrap') diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index fc0add1..8ef1dc0 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -8,6 +8,8 @@ */ pcilib_t* __ctx = 0; +char* full_log = NULL; + /*! * \brief Wraping for vsnprintf function, that saves string to char* * \return saved from vsnprintf string @@ -52,23 +54,51 @@ char* make_str(const char* msg, ...) */ void pcilib_print_error_to_py(void *arg, const char *file, int line, pcilib_log_priority_t prio, const char *msg, - va_list va) { - char* buf_raw_msg = vmake_str(msg, va); - char* buf_wrapped_message = make_str("%s [%s:%d]\n", buf_raw_msg, file, line); - - printf("%s", buf_wrapped_message); - PyErr_SetString(PyExc_Exception, buf_wrapped_message); + va_list va) { + //wrap error message with file and line number + char* buf_raw_msg = vmake_str(msg, va); + char* buf_wrapped_message = make_str("%s [%s:%d]\n", buf_raw_msg, file, line); + + if(prio == PCILIB_LOG_ERROR) + { + if(!full_log) + full_log = make_str(""); - free(buf_wrapped_message); - free(buf_raw_msg); + if(strlen(buf_wrapped_message) >= 2 && + buf_wrapped_message[0] == '#' && + buf_wrapped_message[1] == 'E') + { + char* wrapped_exeption = make_str("%sprogramm error log:\n%s", &(buf_wrapped_message[2]), full_log); + free(full_log); + full_log = NULL; + + PyErr_SetString(PyExc_Exception, wrapped_exeption); + free(wrapped_exeption); + } + else + { + //copy received message to log + char* buf = full_log; + char* buf_start = buf; + full_log = make_str("%s%s", buf, buf_wrapped_message); + free(buf); + } + } + else + printf(buf_wrapped_message); + + free(buf_wrapped_message); + free(buf_raw_msg); } /*! - * \brief Inits pcipywrap module at importing + * \brief Redirect pcilib standart log stream to exeption text. + * Logger will accumulate errors untill get message, starts with "#E". + * After that, logger will write last error, and all accumulated errors + * to Python exeption text */ -void init_pcipywrap_module() +void __redirect_logs_to_exeption() { - printf("init_pcipywrap_module\n"); pcilib_set_logger(pcilib_get_logger_min_prio(), pcilib_print_error_to_py, pcilib_get_logger_argument()); @@ -78,17 +108,19 @@ void init_pcipywrap_module() * \brief Wraps for pcilib_open function. * \param[in] fpga_device path to the device file [/dev/fpga0] * \param[in] model specifies the model of hardware, autodetected if NULL is passed - * \return Pointer to pcilib_t, created by pcilib_open, serialized to bytearray; NULL with exeption text, if failed. + * \return Pointer to pcilib_t, created by pcilib_open; NULL with exeption text, if failed. */ PyObject* create_pcilib_instance(const char *fpga_device, const char *model) { //opening device pcilib_t* ctx = pcilib_open(fpga_device, model); if(!ctx) + { + pcilib_error("#E Failed pcilib_open(%s, %s)", fpga_device, model); return NULL; + } - //serializing object - return PyByteArray_FromStringAndSize((const char*)&ctx, sizeof(pcilib_t*)); + return PyCObject_FromVoidPtr((void*)ctx, NULL); } /*! @@ -114,23 +146,18 @@ PyObject* get_curr_pcilib_instance() /*! * \brief Sets pcilib context to wraper. - * \param[in] addr Pointer to pcilib_t, serialized to bytearray + * \param[in] addr Pointer to pcilib_t, serialized to PyCObject * \return 1, serialized to PyObject or NULL with exeption text, if failed. */ PyObject* set_pcilib(PyObject* addr) { - if(!PyByteArray_Check(addr)) + if(!PyCObject_Check(addr)) { - pcilib_error("Incorrect addr type. Only bytearray is allowed"); + pcilib_error("#E Incorrect addr type. Only PyCObject is allowed"); return NULL; } - //deserializing adress - char* pAddr = PyByteArray_AsString(addr); - - //hard copy context adress - for(int i = 0; i < sizeof(pcilib_t*) + 10; i++) - ((char*)&__ctx)[i] = pAddr[i]; + __ctx = (pcilib_t*)PyCObject_AsVoidPtr(addr); return PyInt_FromLong((long)1); } @@ -146,7 +173,7 @@ PyObject* read_register(const char *regname, const char *bank) { if(!__ctx) { - pcilib_error("pcilib_t handler not initialized"); + pcilib_error("#E pcilib_t handler not initialized"); return NULL; } @@ -157,11 +184,17 @@ PyObject* read_register(const char *regname, const char *bank) err = pcilib_read_register(__ctx, bank, regname, ®_value); if(err) + { + pcilib_error("#E Failed pcilib_read_register"); return NULL; + } err = pcilib_set_value_from_register_value(__ctx, &val, reg_value); if(err) + { + pcilib_error("#E Failed pcilib_set_value_from_register_value"); return NULL; + } return pcilib_get_value_as_pyobject(__ctx, &val); } @@ -187,15 +220,24 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) int err; err = pcilib_set_value_from_pyobject(__ctx, val, &val_internal); if(err) + { + pcilib_error("#E Failed pcilib_set_value_from_pyobject"); return NULL; + } reg_value = pcilib_get_value_as_register_value(__ctx, &val_internal, &err); if(err) + { + pcilib_error("#E Failed pcilib_set_value_from_pyobject, (error %i)", err); return NULL; + } err = pcilib_write_register(__ctx, bank, regname, reg_value); if(err) + { + pcilib_error("#E Failed pcilib_set_value_from_pyobject, (error %i)", err); return NULL; + } return PyInt_FromLong((long)1); } @@ -208,7 +250,7 @@ PyObject* get_property(const char *prop) { if(!__ctx) { - pcilib_error("pcilib_t handler not initialized"); + pcilib_error("#E pcilib_t handler not initialized"); return NULL; } @@ -218,7 +260,10 @@ PyObject* get_property(const char *prop) err = pcilib_get_property(__ctx, prop, &val); if(err) + { + pcilib_error("#E Failed pcilib_get_property, (error %i)", err); return NULL; + } return pcilib_get_value_as_pyobject(__ctx, &val); } @@ -235,19 +280,24 @@ PyObject* set_property(PyObject* val, const char *prop) if(!__ctx) { - pcilib_error("pcilib_t handler not initialized"); + pcilib_error("#E pcilib_t handler not initialized"); return NULL; } pcilib_value_t val_internal = {0}; err = pcilib_set_value_from_pyobject(__ctx, val, &val_internal); if(err) + { + pcilib_error("#E pcilib_set_value_from_pyobject, (error %i)", err); return NULL; + } err = pcilib_set_property(__ctx, prop, &val_internal); - if(err) + { + pcilib_error("#E pcilib_set_property, (error %i)", err); return NULL; + } return PyInt_FromLong((long)1); } @@ -452,7 +502,7 @@ PyObject* get_registers_list(const char *bank) { if(!__ctx) { - pcilib_error("pcilib_t handler not initialized"); + pcilib_error("#E pcilib_t handler not initialized"); return NULL; } @@ -475,7 +525,7 @@ PyObject* get_register_info(const char* reg,const char *bank) { if(!__ctx) { - pcilib_error("pcilib_t handler not initialized"); + pcilib_error("#E pcilib_t handler not initialized"); return NULL; } @@ -497,7 +547,7 @@ PyObject* get_property_info(const char* branch) { if(!__ctx) { - pcilib_error("pcilib_t handler not initialized"); + pcilib_error("#E pcilib_t handler not initialized"); return NULL; } diff --git a/pywrap/pcipywrap.i b/pywrap/pcipywrap.i index 95045f3..4b735d2 100644 --- a/pywrap/pcipywrap.i +++ b/pywrap/pcipywrap.i @@ -1,8 +1,6 @@ %module pcipywrap -%init %{ - init_pcipywrap_module(); -%} +extern void __redirect_logs_to_exeption(); extern PyObject* create_pcilib_instance(const char *fpga_device, const char *model = NULL); extern PyObject* set_pcilib(PyObject* addr); diff --git a/pywrap/server.py b/pywrap/server.py index 0da6bc8..d2927fb 100644 --- a/pywrap/server.py +++ b/pywrap/server.py @@ -373,6 +373,9 @@ if __name__ == '__main__': if not 'LD_LIBRARY_PATH' in os.environ: os.environ['LD_LIBRARY_PATH'] = os.environ["APP_PATH"] + "/pcilib" + #redirect logs to exeption + pcipywrap.__redirect_logs_to_exeption() + pcilib_server = BaseHTTPServer.HTTPServer httpd = pcilib_server((HOST_NAME, PORT_NUMBER), PcilibServerHandler) print time.asctime(), "Server Starts - %s:%s" % (HOST_NAME, PORT_NUMBER) -- cgit v1.2.3 From a4f3ac0b00694287e791cd7d753b420976d9f22a Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Fri, 12 Feb 2016 18:12:08 +0100 Subject: Add destructor for returning PyCObject in create_pcilib_instance function --- pywrap/pcipywrap.c | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) (limited to 'pywrap') diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index 8ef1dc0..a33566a 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -79,7 +79,6 @@ void pcilib_print_error_to_py(void *arg, const char *file, int line, { //copy received message to log char* buf = full_log; - char* buf_start = buf; full_log = make_str("%s%s", buf, buf_wrapped_message); free(buf); } @@ -104,6 +103,16 @@ void __redirect_logs_to_exeption() pcilib_get_logger_argument()); } +/*! + * Destructor for pcilib_t + */ +void close_pcilib_instance(void *ctx) +{ + if(ctx == __ctx) + __ctx = NULL; + pcilib_close(ctx); +} + /*! * \brief Wraps for pcilib_open function. * \param[in] fpga_device path to the device file [/dev/fpga0] @@ -120,7 +129,7 @@ PyObject* create_pcilib_instance(const char *fpga_device, const char *model) return NULL; } - return PyCObject_FromVoidPtr((void*)ctx, NULL); + return PyCObject_FromVoidPtr((void*)ctx, close_pcilib_instance); } /*! -- cgit v1.2.3 From 398e756263502a98a0c1887dcf38f7ef1fafa84b Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Mon, 15 Feb 2016 13:41:25 +0100 Subject: Fix memory leaks Add GIL states for int pcilib_script_read and pcilib_script_write functions Correct desctructor for create_pcilib_instance return object --- pywrap/pcipywrap.c | 140 +++++++++++++++++++++++++++++++---------------------- pywrap/server.py | 2 +- 2 files changed, 84 insertions(+), 58 deletions(-) (limited to 'pywrap') diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index a33566a..77da195 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -108,9 +108,8 @@ void __redirect_logs_to_exeption() */ void close_pcilib_instance(void *ctx) { - if(ctx == __ctx) - __ctx = NULL; - pcilib_close(ctx); + if(ctx != __ctx) + pcilib_close(ctx); } /*! @@ -223,17 +222,21 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) return NULL; } + pcilib_value_t val_internal = {0}; pcilib_register_value_t reg_value; int err; + err = pcilib_set_value_from_pyobject(__ctx, val, &val_internal); + if(err) { pcilib_error("#E Failed pcilib_set_value_from_pyobject"); return NULL; } + reg_value = pcilib_get_value_as_register_value(__ctx, &val_internal, &err); if(err) { @@ -242,11 +245,13 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) } err = pcilib_write_register(__ctx, bank, regname, reg_value); + if(err) { pcilib_error("#E Failed pcilib_set_value_from_pyobject, (error %i)", err); return NULL; } + return PyInt_FromLong((long)1); } @@ -311,18 +316,39 @@ PyObject* set_property(PyObject* val, const char *prop) return PyInt_FromLong((long)1); } +/*! + * \brief Wrap for PyDict_SetItem, with decrease reference counting after set. + */ +void pcilib_pydict_set_item(PyObject* dict, PyObject* name, PyObject* value) +{ + PyDict_SetItem(dict, + name, + value); + Py_XDECREF(name); + Py_XDECREF(value); +} + +/*! + * \brief Wrap for PyList_Append, with decrease reference counting after append. + */ +void pcilib_pylist_append(PyObject* list, PyObject* value) +{ + PyList_Append(list, value); + Py_XDECREF(value); +} + void add_pcilib_value_to_dict(PyObject* dict, pcilib_value_t* val, const char *name) { PyObject *py_val = (PyObject*)pcilib_get_value_as_pyobject(__ctx, val); if(py_val) - PyDict_SetItem(dict, - PyString_FromString(name), - py_val); + pcilib_pydict_set_item(dict, + PyString_FromString(name), + py_val); else - PyDict_SetItem(dict, - PyString_FromString("defvalue"), - PyString_FromString("invalid")); + pcilib_pydict_set_item(dict, + PyString_FromString("defvalue"), + PyString_FromString("invalid")); } PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listItem) @@ -330,17 +356,17 @@ PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listI PyObject* pylistItem = PyDict_New(); if(listItem.name) - PyDict_SetItem(pylistItem, + pcilib_pydict_set_item(pylistItem, PyString_FromString("name"), PyString_FromString(listItem.name)); if(listItem.description) - PyDict_SetItem(pylistItem, + pcilib_pydict_set_item(pylistItem, PyString_FromString("description"), PyString_FromString(listItem.description)); if(listItem.path) - PyDict_SetItem(pylistItem, + pcilib_pydict_set_item(pylistItem, PyString_FromString("path"), PyString_FromString(listItem.path)); @@ -363,7 +389,7 @@ PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listI default: break; } - PyDict_SetItem(pylistItem, + pcilib_pydict_set_item(pylistItem, PyString_FromString("type"), PyString_FromString(type)); @@ -372,15 +398,15 @@ PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listI PyObject* modes = PyList_New(0); if((listItem.mode & PCILIB_ACCESS_R ) == PCILIB_REGISTER_R) - PyList_Append(modes, PyString_FromString("R")); + pcilib_pylist_append(modes, PyString_FromString("R")); if((listItem.mode & PCILIB_ACCESS_W ) == PCILIB_REGISTER_W) - PyList_Append(modes, PyString_FromString("W")); + pcilib_pylist_append(modes, PyString_FromString("W")); if((listItem.mode & PCILIB_ACCESS_RW ) == PCILIB_REGISTER_RW) - PyList_Append(modes, PyString_FromString("RW")); + pcilib_pylist_append(modes, PyString_FromString("RW")); if((listItem.mode & PCILIB_REGISTER_INCONSISTENT) == PCILIB_REGISTER_INCONSISTENT) - PyList_Append(modes, PyString_FromString("NO_CHK")); + pcilib_pylist_append(modes, PyString_FromString("NO_CHK")); - PyDict_SetItem(pylistItem, + pcilib_pydict_set_item(pylistItem, PyString_FromString("mode"), modes); @@ -388,14 +414,14 @@ PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listI PyObject* flags = PyList_New(0); if((listItem.flags & PCILIB_LIST_FLAG_CHILDS ) == PCILIB_LIST_FLAG_CHILDS) - PyList_Append(flags, PyString_FromString("childs")); + pcilib_pylist_append(flags, PyString_FromString("childs")); - PyDict_SetItem(pylistItem, + pcilib_pydict_set_item(pylistItem, PyString_FromString("flags"), flags); if(listItem.unit) - PyDict_SetItem(pylistItem, + pcilib_pydict_set_item(pylistItem, PyString_FromString("unit"), PyString_FromString(listItem.unit)); @@ -407,44 +433,44 @@ PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listI PyObject* pylistItem = PyDict_New(); if(listItem.name) - PyDict_SetItem(pylistItem, - PyString_FromString("name"), - PyString_FromString(listItem.name)); + pcilib_pydict_set_item(pylistItem, + PyString_FromString("name"), + PyString_FromString(listItem.name)); if(listItem.description) - PyDict_SetItem(pylistItem, - PyString_FromString("description"), - PyString_FromString(listItem.description)); + pcilib_pydict_set_item(pylistItem, + PyString_FromString("description"), + PyString_FromString(listItem.description)); if(listItem.bank) - PyDict_SetItem(pylistItem, - PyString_FromString("bank"), - PyString_FromString(listItem.bank)); + pcilib_pydict_set_item(pylistItem, + PyString_FromString("bank"), + PyString_FromString(listItem.bank)); //serialize modes PyObject* modes = PyList_New(0); if((listItem.mode & PCILIB_REGISTER_R) == PCILIB_REGISTER_R) - PyList_Append(modes, PyString_FromString("R")); + pcilib_pylist_append(modes, PyString_FromString("R")); if((listItem.mode & PCILIB_REGISTER_W) == PCILIB_REGISTER_W) - PyList_Append(modes, PyString_FromString("W")); + pcilib_pylist_append(modes, PyString_FromString("W")); if((listItem.mode & PCILIB_REGISTER_RW) == PCILIB_REGISTER_RW) - PyList_Append(modes, PyString_FromString("RW")); + pcilib_pylist_append(modes, PyString_FromString("RW")); if((listItem.mode & PCILIB_REGISTER_W1C) == PCILIB_REGISTER_W1C) - PyList_Append(modes, PyString_FromString("W1C")); + pcilib_pylist_append(modes, PyString_FromString("W1C")); if((listItem.mode & PCILIB_REGISTER_RW1C) == PCILIB_REGISTER_RW1C) - PyList_Append(modes, PyString_FromString("RW1C")); + pcilib_pylist_append(modes, PyString_FromString("RW1C")); if((listItem.mode & PCILIB_REGISTER_W1I) == PCILIB_REGISTER_W1I) - PyList_Append(modes, PyString_FromString("W1I")); + pcilib_pylist_append(modes, PyString_FromString("W1I")); if((listItem.mode & PCILIB_REGISTER_RW1I) == PCILIB_REGISTER_RW1I) - PyList_Append(modes, PyString_FromString("RW1I")); + pcilib_pylist_append(modes, PyString_FromString("RW1I")); if((listItem.mode & PCILIB_REGISTER_INCONSISTENT) == PCILIB_REGISTER_INCONSISTENT) - PyList_Append(modes, PyString_FromString("NO_CHK")); + pcilib_pylist_append(modes, PyString_FromString("NO_CHK")); - PyDict_SetItem(pylistItem, - PyString_FromString("mode"), - modes); - + pcilib_pydict_set_item(pylistItem, + PyString_FromString("mode"), + modes); + pcilib_value_t defval = {0}; pcilib_set_value_from_register_value(__ctx, &defval, listItem.defvalue); add_pcilib_value_to_dict(pylistItem, &defval, "defvalue"); @@ -460,9 +486,9 @@ PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listI PyObject* range = PyDict_New(); add_pcilib_value_to_dict(range, &minval, "min"); add_pcilib_value_to_dict(range, &maxval, "max"); - PyDict_SetItem(pylistItem, - PyString_FromString("range"), - range); + pcilib_pydict_set_item(pylistItem, + PyString_FromString("range"), + range); } if(listItem.values) @@ -487,21 +513,21 @@ PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listI add_pcilib_value_to_dict(valuesItem, &max, "max"); if(listItem.values[j].name) - PyDict_SetItem(valuesItem, - PyString_FromString("name"), - PyString_FromString(listItem.values[j].name)); + pcilib_pydict_set_item(valuesItem, + PyString_FromString("name"), + PyString_FromString(listItem.values[j].name)); if(listItem.values[j].description) - PyDict_SetItem(valuesItem, - PyString_FromString("name"), - PyString_FromString(listItem.values[j].description)); + pcilib_pydict_set_item(valuesItem, + PyString_FromString("name"), + PyString_FromString(listItem.values[j].description)); - PyList_Append(values, valuesItem); + pcilib_pylist_append(values, valuesItem); } - PyDict_SetItem(pylistItem, - PyString_FromString("values"), - values); + pcilib_pydict_set_item(pylistItem, + PyString_FromString("values"), + values); } return pylistItem; @@ -522,7 +548,7 @@ PyObject* get_registers_list(const char *bank) { //serialize item attributes PyObject* pylistItem = pcilib_convert_register_info_to_pyobject(list[i]); - PyList_Append(pyList, pylistItem); + pcilib_pylist_append(pyList, pylistItem); } pcilib_free_register_info(__ctx, list); @@ -568,7 +594,7 @@ PyObject* get_property_info(const char* branch) { //serialize item attributes PyObject* pylistItem = pcilib_convert_property_info_to_pyobject(list[i]); - PyList_Append(pyList, pylistItem); + pcilib_pylist_append(pyList, pylistItem); } pcilib_free_property_info(__ctx, list); diff --git a/pywrap/server.py b/pywrap/server.py index d2927fb..f55d43a 100644 --- a/pywrap/server.py +++ b/pywrap/server.py @@ -105,7 +105,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): #parse command arguments and convert them to string branch = data.get('branch', None) if not branch is None: - branch = str(bank) + branch = str(branch) properties = dict() try: -- cgit v1.2.3 From fc80d8b64672785b4d9c7127e852ca9bf19c9194 Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Mon, 15 Feb 2016 16:09:37 +0100 Subject: Add options parsing to server\n Rename get_property_info for get_property_list --- pywrap/pcipywrap.c | 2 +- pywrap/pcipywrap.i | 2 +- pywrap/server.py | 93 +++++++++++++++++++++++++++++------------------------- 3 files changed, 52 insertions(+), 45 deletions(-) (limited to 'pywrap') diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index 77da195..b1ee630 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -578,7 +578,7 @@ PyObject* get_register_info(const char* reg,const char *bank) return py_info; } -PyObject* get_property_info(const char* branch) +PyObject* get_property_list(const char* branch) { if(!__ctx) { diff --git a/pywrap/pcipywrap.i b/pywrap/pcipywrap.i index 4b735d2..86b6f36 100644 --- a/pywrap/pcipywrap.i +++ b/pywrap/pcipywrap.i @@ -16,4 +16,4 @@ extern PyObject* set_property(PyObject* val, const char *prop); extern PyObject* get_registers_list(const char *bank = NULL); extern PyObject* get_register_info(const char* reg,const char *bank = NULL); -extern PyObject* get_property_info(const char* branch = NULL); +extern PyObject* get_property_list(const char* branch = NULL); diff --git a/pywrap/server.py b/pywrap/server.py index f55d43a..acba791 100644 --- a/pywrap/server.py +++ b/pywrap/server.py @@ -4,7 +4,7 @@ import pcipywrap import json import BaseHTTPServer import sys -import getopt +from optparse import OptionParser class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): @@ -23,33 +23,33 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): command = data['command'] if(command == 'help'): s.help(data) - - elif(command == 'open'): - #check required arguments - if not 'device' in data: - s.error('message doesnt contains "device" field, ' - 'which is required for "open" command', data) - return - #parse command arguments and convert them to string - device = str(data.get('device', None)) - model = data.get('model', None) - if not model is None: - model = str(model) - try: - s.openPcilibInstance(device, model) - except Exception as e: - s.error(str(e), data) - return - - #Success! Create and send reply - s.send_response(200) - s.send_header('content-type', 'application/json') - s.end_headers() - out = dict() - out['status'] = 'ok' - s.wrapMessageAndSend(out, data) - + #elif(command == 'open'): + # #check required arguments + # if not 'device' in data: + # s.error('message doesnt contains "device" field, ' + # 'which is required for "open" command', data) + # return + # #parse command arguments and convert them to string + # device = str(data.get('device', None)) + # model = data.get('model', None) + # if not model is None: + # model = str(model) + # + # try: + # s.openPcilibInstance(device, model) + # except Exception as e: + # s.error(str(e), data) + # return + # + # #Success! Create and send reply + # s.send_response(200) + # s.send_header('content-type', 'application/json') + # s.end_headers() + # out = dict() + # out['status'] = 'ok' + # s.wrapMessageAndSend(out, data) + elif(command == 'get_registers_list'): #parse command arguments and convert them to string bank = data.get('bank', None) @@ -101,7 +101,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): out['register'] = register s.wrapMessageAndSend(out, data) - elif(command == 'get_property_info'): + elif(command == 'get_property_list'): #parse command arguments and convert them to string branch = data.get('branch', None) if not branch is None: @@ -109,7 +109,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): properties = dict() try: - properties = pcipywrap.get_property_info(branch) + properties = pcipywrap.get_property_list(branch) except Exception as e: s.error(str(e), data) return @@ -294,7 +294,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): ' bank: - if set, only register within the specified bank will be returned\n' '\n' - ' command: get_property_info - Returns the list of properties available under the specified path.\n' + ' command: get_property_list - Returns the list of properties available under the specified path.\n' ' optional fields\n' ' branch: - Path. If not set, will return the top-level properties\n' '\n' @@ -344,21 +344,25 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): message['received_message'] = received_message s.wfile.write(json.dumps(message)) - if __name__ == '__main__': - HOST_NAME = '' # !!!REMEMBER TO CHANGE THIS!!! - PORT_NUMBER = 12412 # Maybe set this to 9000. + #parce command line options + parser = OptionParser() + parser.add_option("-p", "--port", action="store", + type="int", dest="port", default=9000, + help="Set server port (8888)") + parser.add_option("-d", "--device", action="store", + type="string", dest="device", default=str('/dev/fpga0'), + help="FPGA device (/dev/fpga0)") + parser.add_option("-m", "--model", action="store", + type="string", dest="model", default=None, + help="Memory model (autodetected)") + opts = parser.parse_args()[0] - try: - opts, args = getopt.getopt(sys.argv[1:], "", []) - #opts, args = getopt.getopt(sys.argv[1:], "hop:v", ["help", "output="]) - #print opts, args - except getopt.GetoptError as err: - # print help information and exit: - print str(err) # will print something like "option -a not recognized" - #usage() - sys.exit(2) + HOST_NAME = '' + PORT_NUMBER = opts.port + MODEL = opts.model + DEVICE = opts.device #Set enviroment variables, if it not setted already if not 'APP_PATH' in os.environ: @@ -373,9 +377,12 @@ if __name__ == '__main__': if not 'LD_LIBRARY_PATH' in os.environ: os.environ['LD_LIBRARY_PATH'] = os.environ["APP_PATH"] + "/pcilib" - #redirect logs to exeption + #create pcilib instance and redirect logs to exeption + lib = pcipywrap.create_pcilib_instance(opts.device, opts.model) + pcipywrap.set_pcilib(lib) pcipywrap.__redirect_logs_to_exeption() + #start server pcilib_server = BaseHTTPServer.HTTPServer httpd = pcilib_server((HOST_NAME, PORT_NUMBER), PcilibServerHandler) print time.asctime(), "Server Starts - %s:%s" % (HOST_NAME, PORT_NUMBER) -- cgit v1.2.3 From ed9d8f285f4d81e1ce8bb5e7a5b9e471a73c1590 Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Tue, 16 Feb 2016 16:30:40 +0100 Subject: 1. Add python thread initialization to pcilib_init_py() -Fix pcilib_script_run_func() work in multithread mode 2. pcilib_close() - Move free_py() code after free views to make view destructors work properly 3. Move script hash to pcilib_py_s 4. Move pcilib_get_logger() pcilib_get_logger_min_prio() and pcilib_get_logger_argument() declarations to error.h 5. Refactor pcilib_get_value_as_pyobject pcilib_set_value_from_pyobject to more unified form 6. Add more memory checks. Fix some string memory allocations. 7. Refactor pcilib_py_s member names. 8. Merge pcilib_script_read() and pcilib_script_write() to pcilib_script_run_func() 9. Update test_pywrap views scripts --- pywrap/pcipywrap.c | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) (limited to 'pywrap') diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index b1ee630..40dbdfc 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -127,7 +127,6 @@ PyObject* create_pcilib_instance(const char *fpga_device, const char *model) pcilib_error("#E Failed pcilib_open(%s, %s)", fpga_device, model); return NULL; } - return PyCObject_FromVoidPtr((void*)ctx, close_pcilib_instance); } @@ -204,7 +203,7 @@ PyObject* read_register(const char *regname, const char *bank) return NULL; } - return pcilib_get_value_as_pyobject(__ctx, &val); + return pcilib_get_value_as_pyobject(__ctx, &val, NULL); } /*! @@ -228,7 +227,7 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) int err; - err = pcilib_set_value_from_pyobject(__ctx, val, &val_internal); + err = pcilib_set_value_from_pyobject(__ctx, &val_internal, val); if(err) { @@ -279,7 +278,7 @@ PyObject* get_property(const char *prop) return NULL; } - return pcilib_get_value_as_pyobject(__ctx, &val); + return pcilib_get_value_as_pyobject(__ctx, &val, NULL); } /*! @@ -299,7 +298,7 @@ PyObject* set_property(PyObject* val, const char *prop) } pcilib_value_t val_internal = {0}; - err = pcilib_set_value_from_pyobject(__ctx, val, &val_internal); + err = pcilib_set_value_from_pyobject(__ctx, &val_internal, val); if(err) { pcilib_error("#E pcilib_set_value_from_pyobject, (error %i)", err); @@ -339,7 +338,7 @@ void pcilib_pylist_append(PyObject* list, PyObject* value) void add_pcilib_value_to_dict(PyObject* dict, pcilib_value_t* val, const char *name) { - PyObject *py_val = (PyObject*)pcilib_get_value_as_pyobject(__ctx, val); + PyObject *py_val = (PyObject*)pcilib_get_value_as_pyobject(__ctx, val, NULL); if(py_val) pcilib_pydict_set_item(dict, -- cgit v1.2.3 From 3269dce32883e14b45cc490a0cc0037b4c808a68 Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Wed, 17 Feb 2016 11:01:22 +0100 Subject: 1. Add cmake BUILD_PYTHON_MODULES option. 2. Rename log options getting functions. 3. py: - pcilib_init_py() - extract pcilib_py_add_script_dir() - pcilib_py_init_script() - extract view-specialized code to pcilib_py_get_transform_script_properties() 3. pcilib_open(): - move pcilib_init_py() to previous position. - add extract pcilib_py_add_script_dir() 4. pcilib_script_s - change hash key. Now it is (const char*) and contains script file name with extension 5. pcipywrap: - Add pcipywrap.h to remove swig generated file complile warnings - remove -includeall swig flag to prevent crash in multi-thread scripts - change set python expetion mechanic --- pywrap/CMakeLists.txt | 5 +- pywrap/pcipywrap.c | 135 ++++++++++++++++++-------------------------------- pywrap/pcipywrap.i | 4 ++ 3 files changed, 53 insertions(+), 91 deletions(-) (limited to 'pywrap') diff --git a/pywrap/CMakeLists.txt b/pywrap/CMakeLists.txt index e5f7ea7..d4d75d1 100644 --- a/pywrap/CMakeLists.txt +++ b/pywrap/CMakeLists.txt @@ -8,14 +8,13 @@ include_directories( ${UTHASH_INCLUDE_DIRS} ) +set(HEADERS pcipywrap.h) + #Creating python wrapping INCLUDE(${SWIG_USE_FILE}) - INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}) - SET(CMAKE_SWIG_FLAGS "") -SET_SOURCE_FILES_PROPERTIES(pcipywrap.i PROPERTIES SWIG_FLAGS "-includeall") SWIG_ADD_MODULE(pcipywrap python pcipywrap.i pcipywrap.c) SWIG_LINK_LIBRARIES(pcipywrap ${PYTHON_LIBRARIES} pcilib) diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index 40dbdfc..639fa15 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -1,6 +1,4 @@ -#include "pci.h" -#include "error.h" -#include +#include "pcipywrap.h" /*! * \brief Global pointer to pcilib_t context. @@ -63,25 +61,11 @@ void pcilib_print_error_to_py(void *arg, const char *file, int line, { if(!full_log) full_log = make_str(""); - - if(strlen(buf_wrapped_message) >= 2 && - buf_wrapped_message[0] == '#' && - buf_wrapped_message[1] == 'E') - { - char* wrapped_exeption = make_str("%sprogramm error log:\n%s", &(buf_wrapped_message[2]), full_log); - free(full_log); - full_log = NULL; - PyErr_SetString(PyExc_Exception, wrapped_exeption); - free(wrapped_exeption); - } - else - { - //copy received message to log - char* buf = full_log; - full_log = make_str("%s%s", buf, buf_wrapped_message); - free(buf); - } + //copy received message to log + char* buf = full_log; + full_log = make_str("%s%s", buf, buf_wrapped_message); + free(buf); } else printf(buf_wrapped_message); @@ -90,17 +74,35 @@ void pcilib_print_error_to_py(void *arg, const char *file, int line, free(buf_raw_msg); } -/*! - * \brief Redirect pcilib standart log stream to exeption text. - * Logger will accumulate errors untill get message, starts with "#E". - * After that, logger will write last error, and all accumulated errors - * to Python exeption text - */ +void set_python_exception(const char* msg, ...) +{ + va_list vl; + va_start(vl, msg); + char *buf = vmake_str(msg, vl); + + char* wrapped_exeption; + if(full_log) + wrapped_exeption = make_str("%s\nprogramm error log:\n%s", buf, full_log); + else + wrapped_exeption = buf; + + free(full_log); + full_log = NULL; + + PyErr_SetString(PyExc_Exception, wrapped_exeption); + + free(buf); + if(full_log) + free(wrapped_exeption); + va_end(vl); +} + + void __redirect_logs_to_exeption() { - pcilib_set_logger(pcilib_get_logger_min_prio(), + pcilib_set_logger(pcilib_get_log_level(), pcilib_print_error_to_py, - pcilib_get_logger_argument()); + pcilib_get_logger_context()); } /*! @@ -112,27 +114,18 @@ void close_pcilib_instance(void *ctx) pcilib_close(ctx); } -/*! - * \brief Wraps for pcilib_open function. - * \param[in] fpga_device path to the device file [/dev/fpga0] - * \param[in] model specifies the model of hardware, autodetected if NULL is passed - * \return Pointer to pcilib_t, created by pcilib_open; NULL with exeption text, if failed. - */ PyObject* create_pcilib_instance(const char *fpga_device, const char *model) { //opening device pcilib_t* ctx = pcilib_open(fpga_device, model); if(!ctx) { - pcilib_error("#E Failed pcilib_open(%s, %s)", fpga_device, model); + set_python_exception("Failed pcilib_open(%s, %s)", fpga_device, model); return NULL; } return PyCObject_FromVoidPtr((void*)ctx, close_pcilib_instance); } -/*! - * \brief Closes current pciliv instance, if its open. - */ void close_curr_pcilib_instance() { if(__ctx) @@ -142,25 +135,16 @@ void close_curr_pcilib_instance() } } -/*! - * \brief Returns current opened pcilib_t instatnce - * \return Pointer to pcilib_t, serialized to bytearray - */ PyObject* get_curr_pcilib_instance() { return PyByteArray_FromStringAndSize((const char*)&__ctx, sizeof(pcilib_t*)); } -/*! - * \brief Sets pcilib context to wraper. - * \param[in] addr Pointer to pcilib_t, serialized to PyCObject - * \return 1, serialized to PyObject or NULL with exeption text, if failed. - */ PyObject* set_pcilib(PyObject* addr) { if(!PyCObject_Check(addr)) { - pcilib_error("#E Incorrect addr type. Only PyCObject is allowed"); + set_python_exception("Incorrect addr type. Only PyCObject is allowed"); return NULL; } @@ -169,18 +153,11 @@ PyObject* set_pcilib(PyObject* addr) return PyInt_FromLong((long)1); } - -/*! - * \brief Reads register value. Wrap for pcilib_read_register function. - * \param[in] regname the name of the register - * \param[in] bank should specify the bank name if register with the same name may occur in multiple banks, NULL otherwise - * \return register value, can be integer or float type; NULL with exeption text, if failed. - */ PyObject* read_register(const char *regname, const char *bank) { if(!__ctx) { - pcilib_error("#E pcilib_t handler not initialized"); + set_python_exception("pcilib_t handler not initialized"); return NULL; } @@ -192,27 +169,20 @@ PyObject* read_register(const char *regname, const char *bank) err = pcilib_read_register(__ctx, bank, regname, ®_value); if(err) { - pcilib_error("#E Failed pcilib_read_register"); + set_python_exception("Failed pcilib_read_register"); return NULL; } err = pcilib_set_value_from_register_value(__ctx, &val, reg_value); if(err) { - pcilib_error("#E Failed pcilib_set_value_from_register_value"); + set_python_exception("Failed pcilib_set_value_from_register_value"); return NULL; } return pcilib_get_value_as_pyobject(__ctx, &val, NULL); } -/*! - * \brief Writes value to register. Wrap for pcilib_write_register function. - * \param[in] val Register value, that needs to be set. Can be int, float or string. - * \param[in] regname the name of the register - * \param[in] bank should specify the bank name if register with the same name may occur in multiple banks, NULL otherwise - * \return 1, serialized to PyObject or NULL with exeption text, if failed. - */ PyObject* write_register(PyObject* val, const char *regname, const char *bank) { if(!__ctx) @@ -231,7 +201,7 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) if(err) { - pcilib_error("#E Failed pcilib_set_value_from_pyobject"); + set_python_exception("Failed pcilib_set_value_from_pyobject"); return NULL; } @@ -239,7 +209,7 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) reg_value = pcilib_get_value_as_register_value(__ctx, &val_internal, &err); if(err) { - pcilib_error("#E Failed pcilib_set_value_from_pyobject, (error %i)", err); + set_python_exception("Failed pcilib_set_value_from_pyobject, (error %i)", err); return NULL; } @@ -247,23 +217,18 @@ PyObject* write_register(PyObject* val, const char *regname, const char *bank) if(err) { - pcilib_error("#E Failed pcilib_set_value_from_pyobject, (error %i)", err); + set_python_exception("Failed pcilib_set_value_from_pyobject, (error %i)", err); return NULL; } return PyInt_FromLong((long)1); } -/*! - * \brief Reads propety value. Wrap for pcilib_get_property function. - * \param[in] prop property name (full name including path) - * \return property value, can be integer or float type; NULL with exeption text, if failed. - */ PyObject* get_property(const char *prop) { if(!__ctx) { - pcilib_error("#E pcilib_t handler not initialized"); + set_python_exception("pcilib_t handler not initialized"); return NULL; } @@ -274,26 +239,20 @@ PyObject* get_property(const char *prop) if(err) { - pcilib_error("#E Failed pcilib_get_property, (error %i)", err); + set_python_exception("Failed pcilib_get_property, (error %i)", err); return NULL; } return pcilib_get_value_as_pyobject(__ctx, &val, NULL); } -/*! - * \brief Writes value to property. Wrap for pcilib_set_property function. - * \param[in] prop property name (full name including path) - * \param[in] val Property value, that needs to be set. Can be int, float or string. - * \return 1, serialized to PyObject or NULL with exeption text, if failed. - */ PyObject* set_property(PyObject* val, const char *prop) { int err; if(!__ctx) { - pcilib_error("#E pcilib_t handler not initialized"); + set_python_exception("pcilib_t handler not initialized"); return NULL; } @@ -301,14 +260,14 @@ PyObject* set_property(PyObject* val, const char *prop) err = pcilib_set_value_from_pyobject(__ctx, &val_internal, val); if(err) { - pcilib_error("#E pcilib_set_value_from_pyobject, (error %i)", err); + set_python_exception("pcilib_set_value_from_pyobject, (error %i)", err); return NULL; } err = pcilib_set_property(__ctx, prop, &val_internal); if(err) { - pcilib_error("#E pcilib_set_property, (error %i)", err); + set_python_exception("pcilib_set_property, (error %i)", err); return NULL; } @@ -536,7 +495,7 @@ PyObject* get_registers_list(const char *bank) { if(!__ctx) { - pcilib_error("#E pcilib_t handler not initialized"); + set_python_exception("pcilib_t handler not initialized"); return NULL; } @@ -559,7 +518,7 @@ PyObject* get_register_info(const char* reg,const char *bank) { if(!__ctx) { - pcilib_error("#E pcilib_t handler not initialized"); + set_python_exception("pcilib_t handler not initialized"); return NULL; } @@ -581,7 +540,7 @@ PyObject* get_property_list(const char* branch) { if(!__ctx) { - pcilib_error("#E pcilib_t handler not initialized"); + set_python_exception("pcilib_t handler not initialized"); return NULL; } diff --git a/pywrap/pcipywrap.i b/pywrap/pcipywrap.i index 86b6f36..952e145 100644 --- a/pywrap/pcipywrap.i +++ b/pywrap/pcipywrap.i @@ -1,5 +1,9 @@ %module pcipywrap +%{ +#include "pcipywrap.h" +%} + extern void __redirect_logs_to_exeption(); extern PyObject* create_pcilib_instance(const char *fpga_device, const char *model = NULL); -- cgit v1.2.3 From 9a9ffd5594a5d27bbecf6160de2c33d44870f5bd Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Wed, 17 Feb 2016 17:20:25 +0100 Subject: Refactor pcipywrap to object --- pywrap/pcipywrap.c | 380 +++++++++++++++++++++++------------------------------ pywrap/pcipywrap.h | 68 ++++++++++ pywrap/pcipywrap.i | 32 ++--- pywrap/server.py | 39 +++--- 4 files changed, 268 insertions(+), 251 deletions(-) create mode 100644 pywrap/pcipywrap.h (limited to 'pywrap') diff --git a/pywrap/pcipywrap.c b/pywrap/pcipywrap.c index 639fa15..11e3ce7 100644 --- a/pywrap/pcipywrap.c +++ b/pywrap/pcipywrap.c @@ -1,11 +1,5 @@ #include "pcipywrap.h" -/*! - * \brief Global pointer to pcilib_t context. - * Used by set_pcilib and read_register. - */ -pcilib_t* __ctx = 0; - char* full_log = NULL; /*! @@ -34,6 +28,7 @@ char* vmake_str(const char* msg, va_list vl) return buf; } + /*! * \brief Wraping for vsnprintf function, that saves string to char* * \return saved from vsnprintf string @@ -105,175 +100,6 @@ void __redirect_logs_to_exeption() pcilib_get_logger_context()); } -/*! - * Destructor for pcilib_t - */ -void close_pcilib_instance(void *ctx) -{ - if(ctx != __ctx) - pcilib_close(ctx); -} - -PyObject* create_pcilib_instance(const char *fpga_device, const char *model) -{ - //opening device - pcilib_t* ctx = pcilib_open(fpga_device, model); - if(!ctx) - { - set_python_exception("Failed pcilib_open(%s, %s)", fpga_device, model); - return NULL; - } - return PyCObject_FromVoidPtr((void*)ctx, close_pcilib_instance); -} - -void close_curr_pcilib_instance() -{ - if(__ctx) - { - pcilib_close(__ctx); - __ctx = NULL; - } -} - -PyObject* get_curr_pcilib_instance() -{ - return PyByteArray_FromStringAndSize((const char*)&__ctx, sizeof(pcilib_t*)); -} - -PyObject* set_pcilib(PyObject* addr) -{ - if(!PyCObject_Check(addr)) - { - set_python_exception("Incorrect addr type. Only PyCObject is allowed"); - return NULL; - } - - __ctx = (pcilib_t*)PyCObject_AsVoidPtr(addr); - - return PyInt_FromLong((long)1); -} - -PyObject* read_register(const char *regname, const char *bank) -{ - if(!__ctx) - { - set_python_exception("pcilib_t handler not initialized"); - return NULL; - } - - pcilib_value_t val = {0}; - pcilib_register_value_t reg_value; - - int err; - - err = pcilib_read_register(__ctx, bank, regname, ®_value); - if(err) - { - set_python_exception("Failed pcilib_read_register"); - return NULL; - } - - err = pcilib_set_value_from_register_value(__ctx, &val, reg_value); - if(err) - { - set_python_exception("Failed pcilib_set_value_from_register_value"); - return NULL; - } - - return pcilib_get_value_as_pyobject(__ctx, &val, NULL); -} - -PyObject* write_register(PyObject* val, const char *regname, const char *bank) -{ - if(!__ctx) - { - pcilib_error("pcilib_t handler not initialized"); - return NULL; - } - - - pcilib_value_t val_internal = {0}; - pcilib_register_value_t reg_value; - - int err; - - err = pcilib_set_value_from_pyobject(__ctx, &val_internal, val); - - if(err) - { - set_python_exception("Failed pcilib_set_value_from_pyobject"); - return NULL; - } - - - reg_value = pcilib_get_value_as_register_value(__ctx, &val_internal, &err); - if(err) - { - set_python_exception("Failed pcilib_set_value_from_pyobject, (error %i)", err); - return NULL; - } - - err = pcilib_write_register(__ctx, bank, regname, reg_value); - - if(err) - { - set_python_exception("Failed pcilib_set_value_from_pyobject, (error %i)", err); - return NULL; - } - - return PyInt_FromLong((long)1); -} - -PyObject* get_property(const char *prop) -{ - if(!__ctx) - { - set_python_exception("pcilib_t handler not initialized"); - return NULL; - } - - int err; - pcilib_value_t val = {0}; - - err = pcilib_get_property(__ctx, prop, &val); - - if(err) - { - set_python_exception("Failed pcilib_get_property, (error %i)", err); - return NULL; - } - - return pcilib_get_value_as_pyobject(__ctx, &val, NULL); -} - -PyObject* set_property(PyObject* val, const char *prop) -{ - int err; - - if(!__ctx) - { - set_python_exception("pcilib_t handler not initialized"); - return NULL; - } - - pcilib_value_t val_internal = {0}; - err = pcilib_set_value_from_pyobject(__ctx, &val_internal, val); - if(err) - { - set_python_exception("pcilib_set_value_from_pyobject, (error %i)", err); - return NULL; - } - - err = pcilib_set_property(__ctx, prop, &val_internal); - if(err) - { - set_python_exception("pcilib_set_property, (error %i)", err); - return NULL; - } - - return PyInt_FromLong((long)1); -} - /*! * \brief Wrap for PyDict_SetItem, with decrease reference counting after set. */ @@ -295,9 +121,9 @@ void pcilib_pylist_append(PyObject* list, PyObject* value) Py_XDECREF(value); } -void add_pcilib_value_to_dict(PyObject* dict, pcilib_value_t* val, const char *name) +void add_pcilib_value_to_dict(pcilib_t* ctx, PyObject* dict, pcilib_value_t* val, const char *name) { - PyObject *py_val = (PyObject*)pcilib_get_value_as_pyobject(__ctx, val, NULL); + PyObject *py_val = (PyObject*)pcilib_get_value_as_pyobject(ctx, val, NULL); if(py_val) pcilib_pydict_set_item(dict, @@ -309,7 +135,7 @@ void add_pcilib_value_to_dict(PyObject* dict, pcilib_value_t* val, const char *n PyString_FromString("invalid")); } -PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listItem) +PyObject * pcilib_convert_property_info_to_pyobject(pcilib_t* ctx, pcilib_property_info_t listItem) { PyObject* pylistItem = PyDict_New(); @@ -386,7 +212,7 @@ PyObject * pcilib_convert_property_info_to_pyobject(pcilib_property_info_t listI return pylistItem; } -PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listItem) +PyObject * pcilib_convert_register_info_to_pyobject(pcilib_t* ctx, pcilib_register_info_t listItem) { PyObject* pylistItem = PyDict_New(); @@ -430,20 +256,20 @@ PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listI modes); pcilib_value_t defval = {0}; - pcilib_set_value_from_register_value(__ctx, &defval, listItem.defvalue); - add_pcilib_value_to_dict(pylistItem, &defval, "defvalue"); + pcilib_set_value_from_register_value(ctx, &defval, listItem.defvalue); + add_pcilib_value_to_dict(ctx, pylistItem, &defval, "defvalue"); if(listItem.range) { pcilib_value_t minval = {0}; - pcilib_set_value_from_register_value(__ctx, &minval, listItem.range->min); - + pcilib_set_value_from_register_value(ctx, &minval, listItem.range->min); + pcilib_value_t maxval = {0}; - pcilib_set_value_from_register_value(__ctx, &maxval, listItem.range->max); + pcilib_set_value_from_register_value(ctx, &maxval, listItem.range->max); PyObject* range = PyDict_New(); - add_pcilib_value_to_dict(range, &minval, "min"); - add_pcilib_value_to_dict(range, &maxval, "max"); + add_pcilib_value_to_dict(ctx, range, &minval, "min"); + add_pcilib_value_to_dict(ctx, range, &maxval, "max"); pcilib_pydict_set_item(pylistItem, PyString_FromString("range"), range); @@ -458,17 +284,17 @@ PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listI PyObject* valuesItem = PyDict_New(); pcilib_value_t val = {0}; - pcilib_set_value_from_register_value(__ctx, &val, listItem.values[j].value); + pcilib_set_value_from_register_value(ctx, &val, listItem.values[j].value); pcilib_value_t min = {0}; - pcilib_set_value_from_register_value(__ctx, &min, listItem.values[j].min); + pcilib_set_value_from_register_value(ctx, &min, listItem.values[j].min); pcilib_value_t max = {0}; - pcilib_set_value_from_register_value(__ctx, &max, listItem.values[j].max); + pcilib_set_value_from_register_value(ctx, &max, listItem.values[j].max); - add_pcilib_value_to_dict(valuesItem, &val, "value"); - add_pcilib_value_to_dict(valuesItem, &min, "min"); - add_pcilib_value_to_dict(valuesItem, &max, "max"); + add_pcilib_value_to_dict(ctx, valuesItem, &val, "value"); + add_pcilib_value_to_dict(ctx, valuesItem, &min, "min"); + add_pcilib_value_to_dict(ctx, valuesItem, &max, "max"); if(listItem.values[j].name) pcilib_pydict_set_item(valuesItem, @@ -491,71 +317,187 @@ PyObject * pcilib_convert_register_info_to_pyobject(pcilib_register_info_t listI return pylistItem; } -PyObject* get_registers_list(const char *bank) +Pcipywrap *new_Pcipywrap(const char* fpga_device, const char* model) { - if(!__ctx) + //opening device + pcilib_t* ctx = pcilib_open(fpga_device, model); + if(!ctx) + { + set_python_exception("Failed pcilib_open(%s, %s)", fpga_device, model); + return NULL; + } + Pcipywrap *self; + self = (Pcipywrap *) malloc(sizeof(Pcipywrap)); + self->shared = 0; + self->ctx = ctx; + return self; +} + +Pcipywrap *create_Pcipywrap(PyObject* ctx) +{ + if(!PyCObject_Check(ctx)) { - set_python_exception("pcilib_t handler not initialized"); + set_python_exception("Incorrect ctx type. Only PyCObject is allowed"); return NULL; } - pcilib_register_info_t *list = pcilib_get_register_list(__ctx, bank, PCILIB_LIST_FLAGS_DEFAULT); + Pcipywrap *self; + self = (Pcipywrap *) malloc(sizeof(Pcipywrap)); + self->shared = 1; + self->ctx = PyCObject_AsVoidPtr(ctx); + return self; +} + +void delete_Pcipywrap(Pcipywrap *self) { + if(!self->shared) + pcilib_close(self->ctx); + + free(self); +} + +PyObject* Pcipywrap_read_register(Pcipywrap *self, const char *regname, const char *bank) +{ + pcilib_value_t val = {0}; + pcilib_register_value_t reg_value; + + int err; + + err = pcilib_read_register(self->ctx, bank, regname, ®_value); + if(err) + { + set_python_exception("Failed pcilib_read_register"); + return NULL; + } + + err = pcilib_set_value_from_register_value(self->ctx, &val, reg_value); + if(err) + { + set_python_exception("Failed pcilib_set_value_from_register_value"); + return NULL; + } + + return pcilib_get_value_as_pyobject(self->ctx, &val, NULL); +} + +PyObject* Pcipywrap_write_register(Pcipywrap *self, PyObject* val, const char *regname, const char *bank) +{ + pcilib_value_t val_internal = {0}; + pcilib_register_value_t reg_value; + + int err; + + err = pcilib_set_value_from_pyobject(self->ctx, &val_internal, val); + + if(err) + { + set_python_exception("Failed pcilib_set_value_from_pyobject"); + return NULL; + } + + + reg_value = pcilib_get_value_as_register_value(self->ctx, &val_internal, &err); + if(err) + { + set_python_exception("Failed pcilib_set_value_from_pyobject, (error %i)", err); + return NULL; + } + + err = pcilib_write_register(self->ctx, bank, regname, reg_value); + + if(err) + { + set_python_exception("Failed pcilib_set_value_from_pyobject, (error %i)", err); + return NULL; + } + + return PyInt_FromLong((long)1); +} + +PyObject* Pcipywrap_get_property(Pcipywrap *self, const char *prop) +{ + int err; + pcilib_value_t val = {0}; + + err = pcilib_get_property(self->ctx, prop, &val); + + if(err) + { + set_python_exception("Failed pcilib_get_property, (error %i)", err); + return NULL; + } + + return pcilib_get_value_as_pyobject(self->ctx, &val, NULL); +} + +PyObject* Pcipywrap_set_property(Pcipywrap *self, PyObject* val, const char *prop) +{ + int err; + + pcilib_value_t val_internal = {0}; + err = pcilib_set_value_from_pyobject(self->ctx, &val_internal, val); + if(err) + { + set_python_exception("pcilib_set_value_from_pyobject, (error %i)", err); + return NULL; + } + + err = pcilib_set_property(self->ctx, prop, &val_internal); + if(err) + { + set_python_exception("pcilib_set_property, (error %i)", err); + return NULL; + } + + return PyInt_FromLong((long)1); +} + +PyObject* Pcipywrap_get_registers_list(Pcipywrap *self, const char *bank) +{ + pcilib_register_info_t *list = pcilib_get_register_list(self->ctx, bank, PCILIB_LIST_FLAGS_DEFAULT); PyObject* pyList = PyList_New(0); - for(int i = 0; i < __ctx->num_reg; i++) + for(int i = 0; i < ((pcilib_t*)self->ctx)->num_reg; i++) { //serialize item attributes - PyObject* pylistItem = pcilib_convert_register_info_to_pyobject(list[i]); + PyObject* pylistItem = pcilib_convert_register_info_to_pyobject(self->ctx, list[i]); pcilib_pylist_append(pyList, pylistItem); } - pcilib_free_register_info(__ctx, list); + pcilib_free_register_info(self->ctx, list); return pyList; } -PyObject* get_register_info(const char* reg,const char *bank) +PyObject* Pcipywrap_get_register_info(Pcipywrap *self, const char* reg,const char *bank) { - if(!__ctx) - { - set_python_exception("pcilib_t handler not initialized"); - return NULL; - } - - pcilib_register_info_t *info = pcilib_get_register_info(__ctx, bank, reg, PCILIB_LIST_FLAGS_DEFAULT); + pcilib_register_info_t *info = pcilib_get_register_info(self->ctx, bank, reg, PCILIB_LIST_FLAGS_DEFAULT); if(!info) { return NULL; } - PyObject* py_info = pcilib_convert_register_info_to_pyobject(info[0]); + PyObject* py_info = pcilib_convert_register_info_to_pyobject(self->ctx, info[0]); - pcilib_free_register_info(__ctx, info); + pcilib_free_register_info(self->ctx, info); return py_info; } -PyObject* get_property_list(const char* branch) +PyObject* Pcipywrap_get_property_list(Pcipywrap *self, const char* branch) { - if(!__ctx) - { - set_python_exception("pcilib_t handler not initialized"); - return NULL; - } - - pcilib_property_info_t *list = pcilib_get_property_list(__ctx, branch, PCILIB_LIST_FLAGS_DEFAULT); + pcilib_property_info_t *list = pcilib_get_property_list(self->ctx, branch, PCILIB_LIST_FLAGS_DEFAULT); PyObject* pyList = PyList_New(0); for(int i = 0; list[i].path; i++) { //serialize item attributes - PyObject* pylistItem = pcilib_convert_property_info_to_pyobject(list[i]); + PyObject* pylistItem = pcilib_convert_property_info_to_pyobject(self->ctx, list[i]); pcilib_pylist_append(pyList, pylistItem); } - pcilib_free_property_info(__ctx, list); + pcilib_free_property_info(self->ctx, list); return pyList; } diff --git a/pywrap/pcipywrap.h b/pywrap/pcipywrap.h new file mode 100644 index 0000000..8389445 --- /dev/null +++ b/pywrap/pcipywrap.h @@ -0,0 +1,68 @@ +#ifndef PCIPYWRAP_H +#define PCIPYWRAP_H + +#include "pci.h" +#include "error.h" +#include + +typedef struct { + void* ctx; + int shared; +} Pcipywrap; + +/*! + * \brief Redirect pcilib standart log stream to exeption text. + * Logger will accumulate errors untill get message, starts with "#E". + * After that, logger will write last error, and all accumulated errors + * to Python exeption text + */ +void __redirect_logs_to_exeption(); + +/*! + * \brief Wraps for pcilib_open function. + * \param[in] fpga_device path to the device file [/dev/fpga0] + * \param[in] model specifies the model of hardware, autodetected if NULL is passed + * \return Pointer to pcilib_t, created by pcilib_open; NULL with exeption text, if failed. + */ +PyObject* create_pcilib_instance(const char *fpga_device, const char *model); + +Pcipywrap *new_Pcipywrap(const char* fpga_device, const char* model); +Pcipywrap *create_Pcipywrap(PyObject* ctx); +void delete_Pcipywrap(Pcipywrap *self); + +/*! + * \brief Reads register value. Wrap for pcilib_read_register function. + * \param[in] regname the name of the register + * \param[in] bank should specify the bank name if register with the same name may occur in multiple banks, NULL otherwise + * \return register value, can be integer or float type; NULL with exeption text, if failed. + */ +PyObject* Pcipywrap_read_register(Pcipywrap *self, const char *regname, const char *bank); + +/*! + * \brief Writes value to register. Wrap for pcilib_write_register function. + * \param[in] val Register value, that needs to be set. Can be int, float or string. + * \param[in] regname the name of the register + * \param[in] bank should specify the bank name if register with the same name may occur in multiple banks, NULL otherwise + * \return 1, serialized to PyObject or NULL with exeption text, if failed. + */ +PyObject* Pcipywrap_write_register(Pcipywrap *self, PyObject* val, const char *regname, const char *bank); + +/*! + * \brief Reads propety value. Wrap for pcilib_get_property function. + * \param[in] prop property name (full name including path) + * \return property value, can be integer or float type; NULL with exeption text, if failed. + */ +PyObject* Pcipywrap_get_property(Pcipywrap *self, const char *prop); + +/*! + * \brief Writes value to property. Wrap for pcilib_set_property function. + * \param[in] prop property name (full name including path) + * \param[in] val Property value, that needs to be set. Can be int, float or string. + * \return 1, serialized to PyObject or NULL with exeption text, if failed. + */ +PyObject* Pcipywrap_set_property(Pcipywrap *self, PyObject* val, const char *prop); +PyObject* Pcipywrap_get_registers_list(Pcipywrap *self, const char *bank); +PyObject* Pcipywrap_get_register_info(Pcipywrap *self, const char* reg,const char *bank); +PyObject* Pcipywrap_get_property_list(Pcipywrap *self, const char* branch); + +#endif /* PCIPYWRAP_H */ diff --git a/pywrap/pcipywrap.i b/pywrap/pcipywrap.i index 952e145..88a746f 100644 --- a/pywrap/pcipywrap.i +++ b/pywrap/pcipywrap.i @@ -6,18 +6,20 @@ extern void __redirect_logs_to_exeption(); -extern PyObject* create_pcilib_instance(const char *fpga_device, const char *model = NULL); -extern PyObject* set_pcilib(PyObject* addr); -extern void close_curr_pcilib_instance(); -extern PyObject* get_curr_pcilib_instance(); - -extern PyObject* read_register(const char *regname, const char *bank = NULL); -extern PyObject* write_register(PyObject* val, const char *regname, const char *bank = NULL); - -extern PyObject* get_property(const char *prop); -extern PyObject* set_property(PyObject* val, const char *prop); - -extern PyObject* get_registers_list(const char *bank = NULL); -extern PyObject* get_register_info(const char* reg,const char *bank = NULL); - -extern PyObject* get_property_list(const char* branch = NULL); +typedef struct { + %extend { + Pcipywrap(const char* fpga_device = NULL, const char* model = NULL); + Pcipywrap(PyObject* ctx){return create_Pcipywrap(ctx);} + ~Pcipywrap(); + + PyObject* read_register(const char *regname = NULL, const char *bank = NULL); + PyObject* write_register(PyObject* val, const char *regname, const char *bank = NULL); + + PyObject* get_property(const char *prop); + PyObject* set_property(PyObject* val, const char *prop); + + PyObject* get_registers_list(const char *bank = NULL); + PyObject* get_register_info(const char* reg,const char *bank = NULL); + PyObject* get_property_list(const char* branch = NULL); + } +} Pcipywrap; diff --git a/pywrap/server.py b/pywrap/server.py index acba791..03302a2 100644 --- a/pywrap/server.py +++ b/pywrap/server.py @@ -7,7 +7,10 @@ import sys from optparse import OptionParser class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): - + def __init__(s, pcilib, *args): + s.pcilib = pcilib + BaseHTTPServer.BaseHTTPRequestHandler.__init__(s, *args) + def do_HEAD(s): s.send_response(200) s.send_header('content-type', 'application/json') @@ -58,7 +61,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): registers = dict() try: - registers = pcipywrap.get_registers_list(bank) + registers = s.pcilib.get_registers_list(bank) except Exception as e: s.error(str(e), data) return @@ -87,7 +90,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): register = dict() try: - register = pcipywrap.get_register_info(reg, bank) + register = s.pcilib.get_register_info(reg, bank) except Exception as e: s.error(str(e), data) return @@ -109,7 +112,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): properties = dict() try: - properties = pcipywrap.get_property_list(branch) + properties = s.pcilib.get_property_list(branch) except Exception as e: s.error(str(e), data) return @@ -138,7 +141,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): value = 0 try: - value = pcipywrap.read_register(reg, bank) + value = s.pcilib.read_register(reg, bank) except Exception as e: s.error(str(e), data) return @@ -172,7 +175,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): bank = str(bank) try: - pcipywrap.write_register(value, reg, bank) + s.pcilib.write_register(value, reg, bank) except Exception as e: s.error(str(e), data) return @@ -197,7 +200,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): value = 0 try: - value = pcipywrap.get_property(prop) + value = s.pcilib.get_property(prop) except Exception as e: s.error(str(e), data) return @@ -228,7 +231,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): value = str(data.get('value', None)) try: - pcipywrap.set_property(value, prop) + s.pcilib.set_property(value, prop) except Exception as e: s.error(str(e), data) return @@ -255,10 +258,7 @@ class PcilibServerHandler(BaseHTTPServer.BaseHTTPRequestHandler): """open device context """ def openPcilibInstance(s, device, model): - pcipywrap.close_curr_pcilib_instance() - - lib = pcipywrap.create_pcilib_instance(device, model) - pcipywrap.set_pcilib(lib) + s.pcilib = pcipywrap.create_pcilib_instance(device, model) """Send help message""" def help(s, received_message = None): @@ -350,7 +350,7 @@ if __name__ == '__main__': parser = OptionParser() parser.add_option("-p", "--port", action="store", type="int", dest="port", default=9000, - help="Set server port (8888)") + help="Set server port (9000)") parser.add_option("-d", "--device", action="store", type="string", dest="device", default=str('/dev/fpga0'), help="FPGA device (/dev/fpga0)") @@ -377,14 +377,19 @@ if __name__ == '__main__': if not 'LD_LIBRARY_PATH' in os.environ: os.environ['LD_LIBRARY_PATH'] = os.environ["APP_PATH"] + "/pcilib" - #create pcilib instance and redirect logs to exeption - lib = pcipywrap.create_pcilib_instance(opts.device, opts.model) - pcipywrap.set_pcilib(lib) + #redirect logs to exeption pcipywrap.__redirect_logs_to_exeption() #start server pcilib_server = BaseHTTPServer.HTTPServer - httpd = pcilib_server((HOST_NAME, PORT_NUMBER), PcilibServerHandler) + + #pass Pcipywrap to to server handler + lib = pcipywrap.Pcipywrap(DEVICE, MODEL) + def handler(*args): + PcilibServerHandler(lib, *args) + + httpd = pcilib_server((HOST_NAME, PORT_NUMBER), handler) + print time.asctime(), "Server Starts - %s:%s" % (HOST_NAME, PORT_NUMBER) try: httpd.serve_forever() -- cgit v1.2.3 From 52eb7f4fb76ddf99dedf44332aae7af4df76ab36 Mon Sep 17 00:00:00 2001 From: Vasilii Chernov Date: Wed, 17 Feb 2016 18:13:36 +0100 Subject: Add test to repository. Add GIL states to pcilib_set_value_from_pyobject --- pywrap/CMakeLists.txt | 1 + pywrap/test_pcipywrap.py | 119 +++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 120 insertions(+) create mode 100755 pywrap/test_pcipywrap.py (limited to 'pywrap') diff --git a/pywrap/CMakeLists.txt b/pywrap/CMakeLists.txt index d4d75d1..4592c9a 100644 --- a/pywrap/CMakeLists.txt +++ b/pywrap/CMakeLists.txt @@ -19,3 +19,4 @@ SWIG_ADD_MODULE(pcipywrap python pcipywrap.i pcipywrap.c) SWIG_LINK_LIBRARIES(pcipywrap ${PYTHON_LIBRARIES} pcilib) configure_file(server.py server.py) +configure_file(test_pcipywrap.py test_pcipywrap.py) diff --git a/pywrap/test_pcipywrap.py b/pywrap/test_pcipywrap.py new file mode 100755 index 0000000..257b4a5 --- /dev/null +++ b/pywrap/test_pcipywrap.py @@ -0,0 +1,119 @@ +import threading +import pcipywrap +import random +import os +import json +import requests +import time + +class test_pcipywrap(): + def __init__(self, device, model, num_threads = 150, + write_percentage = 0.1, register = 'test_prop2', + server_host = 'http://localhost', server_port = 12412, + server_message_delay = 0): + #initialize enviroment variables + if not 'APP_PATH' in os.environ: + APP_PATH = '' + file_dir = os.path.dirname(os.path.abspath(__file__)) + APP_PATH = str(os.path.abspath(file_dir + '/../..')) + os.environ["APP_PATH"] = APP_PATH + + if not 'PCILIB_MODEL_DIR' in os.environ: + os.environ['PCILIB_MODEL_DIR'] = os.environ["APP_PATH"] + "/xml" + if not 'LD_LIBRARY_PATH' in os.environ: + os.environ['LD_LIBRARY_PATH'] = os.environ["APP_PATH"] + "/pcilib" + + random.seed() + #create pcilib_instance + self.pcilib = pcipywrap.Pcipywrap(device, model) + self.num_threads = num_threads + self.write_percentage = write_percentage + self.register = register + self.server_message_delay = server_message_delay + self.server_port = server_port + self.server_host = server_host + + def testThreadSafeReadWrite(self): + def threadFunc(): + if random.randint(0, 100) >= (self.write_percentage * 100): + ret = self.pcilib.get_property('/test/prop2') + print self.register, ':', ret + del ret + else: + val = random.randint(0, 65536) + print 'set value:', val + self.pcilib.write_register(val, self.register) + try: + while(1): + thread_list = [threading.Thread(target=threadFunc) for i in range(0, self.num_threads)] + for i in range(0, self.num_threads): + thread_list[i].start() + for i in range(0, self.num_threads): + thread_list[i].join() + print 'cycle done' + except KeyboardInterrupt: + print 'testing done' + pass + + def testMemoryLeak(self): + try: + while(1): + #print self.pcilib.create_pcilib_instance('/dev/fpga0','test_pywrap') + + print self.pcilib.get_property_list('/test') + print self.pcilib.get_register_info('test_prop1') + #print self.pcilib.get_registers_list(); + + #print self.pcilib.read_register('reg1') + #print self.pcilib.write_register(12, 'reg1') + + #print self.pcilib.get_property('/test/prop2') + #print self.pcilib.set_property(12, '/test/prop2') + except KeyboardInterrupt: + print 'testing done' + pass + + def testServer(self): + url = str(self.server_host + ':' + str(self.server_port)) + headers = {'content-type': 'application/json'} + payload =[{'com': 'open', 'data2' : '12341'}, + #{'command': 'open', 'device' : '/dev/fpga0', 'model': 'test_pywrap'}, + {'command': 'help'}, + {'command': 'get_registers_list'}, + {'command': 'get_register_info', 'reg': 'reg1'}, + {'command': 'get_property_list'}, + {'command': 'read_register', 'reg': 'reg1'}, + {'command': 'write_register', 'reg': 'reg1'}, + {'command': 'get_property', 'prop': '/test/prop2'}, + {'command': 'set_property', 'prop': '/test/prop2'}] + + def sendRandomMessage(): + message_number = random.randint(1, len(payload) - 1) + print 'message number: ', message_number + payload[message_number]['value'] = random.randint(0, 65535) + r = requests.get(url, data=json.dumps(payload[message_number]), headers=headers) + print json.dumps(r.json(), sort_keys=True, indent=4, separators=(',', ': ')) + + try: + r = requests.get(url, data=json.dumps(payload[1]), headers=headers) + print json.dumps(r.json(), sort_keys=True, indent=3, separators=(',', ': ')) + + while(1): + time.sleep(self.server_message_delay) + thread_list = [threading.Thread(target=sendRandomMessage) for i in range(0, self.num_threads)] + for i in range(0, self.num_threads): + thread_list[i].start() + for i in range(0, self.num_threads): + thread_list[i].join() + print 'cycle done' + + except KeyboardInterrupt: + print 'testing done' + pass + +if __name__ == '__main__': + lib = test_pcipywrap('/dev/fpga0','test_pywrap', num_threads = 150, + write_percentage = 0.1, register = 'test_prop2',server_host = 'http://localhost', server_port = 12412, + server_message_delay = 0) + lib.testThreadSafeReadWrite() + -- cgit v1.2.3