#ifndef __PY_IDA_FPRO__ #define __PY_IDA_FPRO__ // class qfile_t { private: FILE *fp; bool own; qstring fn; //-------------------------------------------------------------------------- void assign(const qfile_t &rhs) { fn = rhs.fn; fp = rhs.fp; own = false; } //-------------------------------------------------------------------------- bool _from_fp(FILE *fp) { if ( fp == nullptr ) return false; own = false; fn.sprnt("", fp); this->fp = fp; return true; } inline void _from_capsule(PyObject *pycapsule) { PYW_GIL_CHECK_LOCKED_SCOPE(); _from_fp((FILE *) PyCapsule_GetPointer(pycapsule, VALID_CAPSULE_NAME)); } public: int __idc_cvt_id__; //-------------------------------------------------------------------------- qfile_t(const qfile_t &rhs) { assign(rhs); } //-------------------------------------------------------------------------- qfile_t(PyObject *pycapsule = nullptr) { fp = nullptr; own = true; fn.qclear(); __idc_cvt_id__ = PY_ICID_OPAQUE; bool ok; { PYW_GIL_CHECK_LOCKED_SCOPE(); ok = pycapsule != nullptr && PyCapsule_IsValid(pycapsule, VALID_CAPSULE_NAME); } if ( ok ) _from_capsule(pycapsule); } //-------------------------------------------------------------------------- bool opened() { return fp != nullptr; } //-------------------------------------------------------------------------- void close() { if ( fp == nullptr ) return; if ( own ) { SWIG_PYTHON_THREAD_BEGIN_ALLOW; qfclose(fp); SWIG_PYTHON_THREAD_END_ALLOW; } fp = nullptr; own = true; } //-------------------------------------------------------------------------- ~qfile_t() { close(); } //-------------------------------------------------------------------------- bool open(const char *filename, const char *mode) { close(); SWIG_PYTHON_THREAD_BEGIN_ALLOW; fp = qfopen(filename, mode); SWIG_PYTHON_THREAD_END_ALLOW; if ( fp == nullptr ) return false; // Save file name fn = filename; own = true; return true; } //-------------------------------------------------------------------------- static qfile_t *from_fp(FILE *fp) { if ( fp == nullptr ) return nullptr; qfile_t *qf = new qfile_t(); qf->own = false; qf->fn.sprnt("", fp); qf->fp = fp; return qf; } //-------------------------------------------------------------------------- // This method can be used to pass a FILE* from C code static qfile_t *from_capsule(PyObject *pycapsule) { return PyCapsule_IsValid(pycapsule, VALID_CAPSULE_NAME) ? from_fp((FILE *) PyCapsule_GetPointer(pycapsule, VALID_CAPSULE_NAME)) : nullptr; } //-------------------------------------------------------------------------- static qfile_t *tmpfile() { FILE *fp; SWIG_PYTHON_THREAD_BEGIN_ALLOW; fp = qtmpfile(); SWIG_PYTHON_THREAD_END_ALLOW; return from_fp(fp); } //-------------------------------------------------------------------------- FILE *get_fp() { return fp; } //-------------------------------------------------------------------------- int seek(int64 offset, int whence) { int rc; SWIG_PYTHON_THREAD_BEGIN_ALLOW; rc = qfseek(fp, offset, whence); SWIG_PYTHON_THREAD_END_ALLOW; return rc; } //-------------------------------------------------------------------------- int64 tell() { int64 rc; SWIG_PYTHON_THREAD_BEGIN_ALLOW; rc = qftell(fp); SWIG_PYTHON_THREAD_END_ALLOW; return rc; } //-------------------------------------------------------------------------- PyObject *readbytes(int size, bool big_endian) { do { char *buf = (char *) malloc(size + 5); if ( buf == nullptr ) break; PYW_GIL_CHECK_LOCKED_SCOPE(); int r; SWIG_PYTHON_THREAD_BEGIN_ALLOW; r = freadbytes(fp, buf, size, big_endian); SWIG_PYTHON_THREAD_END_ALLOW; if ( r != 0 ) { free(buf); break; } PyObject *ret = PyUnicode_FromStringAndSize(buf, r); free(buf); return ret; } while ( false ); Py_RETURN_NONE; } //-------------------------------------------------------------------------- PyObject *read(int size) { do { char *buf = (char *) malloc(size + 5); if ( buf == nullptr ) break; PYW_GIL_CHECK_LOCKED_SCOPE(); int r; SWIG_PYTHON_THREAD_BEGIN_ALLOW; r = qfread(fp, buf, size); SWIG_PYTHON_THREAD_END_ALLOW; if ( r <= 0 ) { free(buf); break; } PyObject *ret = PyUnicode_FromStringAndSize(buf, r); free(buf); return ret; } while ( false ); Py_RETURN_NONE; } //-------------------------------------------------------------------------- PyObject *gets(int size) { do { char *buf = (char *) malloc(size + 5); if ( buf == nullptr ) break; PYW_GIL_CHECK_LOCKED_SCOPE(); char *p; SWIG_PYTHON_THREAD_BEGIN_ALLOW; p = qfgets(buf, size, fp); SWIG_PYTHON_THREAD_END_ALLOW; if ( p == nullptr ) { free(buf); break; } PyObject *ret = PyUnicode_FromString(buf); free(buf); return ret; } while ( false ); Py_RETURN_NONE; } //-------------------------------------------------------------------------- int writebytes(PyObject *py_buf, bool big_endian) { PYW_GIL_CHECK_LOCKED_SCOPE(); char *buf; Py_ssize_t sz; PyBytes_AsStringAndSize(py_buf, &buf, &sz); int rc; SWIG_PYTHON_THREAD_BEGIN_ALLOW; rc = fwritebytes(fp, buf, int(sz), big_endian); SWIG_PYTHON_THREAD_END_ALLOW; return rc; } //-------------------------------------------------------------------------- int write(PyObject *py_buf) { PYW_GIL_CHECK_LOCKED_SCOPE(); if ( !PyUnicode_Check(py_buf) ) return 0; // Just so that there is no risk that the buffer returned by borref_t py_buf_ref(py_buf); qstring buf; PyUnicode_as_qstring(&buf, py_buf); int rc; SWIG_PYTHON_THREAD_BEGIN_ALLOW; rc = qfwrite(fp, buf.c_str(), buf.length()); SWIG_PYTHON_THREAD_END_ALLOW; return rc; } //-------------------------------------------------------------------------- int puts(const char *str) { PYW_GIL_CHECK_LOCKED_SCOPE(); int rc; SWIG_PYTHON_THREAD_BEGIN_ALLOW; rc = qfputs(str, fp); SWIG_PYTHON_THREAD_END_ALLOW; return rc; } //-------------------------------------------------------------------------- int64 size() { PYW_GIL_CHECK_LOCKED_SCOPE(); qoff64_t r; SWIG_PYTHON_THREAD_BEGIN_ALLOW; int pos = qfseek(fp, 0, SEEK_END); r = qftell(fp); qfseek(fp, pos, SEEK_SET); SWIG_PYTHON_THREAD_END_ALLOW; return r; } //-------------------------------------------------------------------------- int flush() { PYW_GIL_CHECK_LOCKED_SCOPE(); int rc; SWIG_PYTHON_THREAD_BEGIN_ALLOW; rc = qflush(fp); SWIG_PYTHON_THREAD_END_ALLOW; return rc; } //-------------------------------------------------------------------------- PyObject *filename() { PYW_GIL_CHECK_LOCKED_SCOPE(); return PyUnicode_FromString(fn.c_str()); } //-------------------------------------------------------------------------- PyObject *get_byte() { PYW_GIL_CHECK_LOCKED_SCOPE(); int ch; SWIG_PYTHON_THREAD_BEGIN_ALLOW; ch = qfgetc(fp); SWIG_PYTHON_THREAD_END_ALLOW; if ( ch == EOF ) Py_RETURN_NONE; return Py_BuildValue("i", ch); } //-------------------------------------------------------------------------- int put_byte(int chr) { PYW_GIL_CHECK_LOCKED_SCOPE(); int rc; SWIG_PYTHON_THREAD_BEGIN_ALLOW; rc = qfputc(chr, fp); SWIG_PYTHON_THREAD_END_ALLOW; return rc; } }; // #endif