17db96d56Sopenharmony_ci 27db96d56Sopenharmony_ci/* fcntl module */ 37db96d56Sopenharmony_ci 47db96d56Sopenharmony_ci#define PY_SSIZE_T_CLEAN 57db96d56Sopenharmony_ci 67db96d56Sopenharmony_ci#include "Python.h" 77db96d56Sopenharmony_ci 87db96d56Sopenharmony_ci#ifdef HAVE_SYS_FILE_H 97db96d56Sopenharmony_ci#include <sys/file.h> 107db96d56Sopenharmony_ci#endif 117db96d56Sopenharmony_ci 127db96d56Sopenharmony_ci#include <sys/ioctl.h> 137db96d56Sopenharmony_ci#include <fcntl.h> 147db96d56Sopenharmony_ci#ifdef HAVE_STROPTS_H 157db96d56Sopenharmony_ci#include <stropts.h> 167db96d56Sopenharmony_ci#endif 177db96d56Sopenharmony_ci 187db96d56Sopenharmony_ci/*[clinic input] 197db96d56Sopenharmony_cimodule fcntl 207db96d56Sopenharmony_ci[clinic start generated code]*/ 217db96d56Sopenharmony_ci/*[clinic end generated code: output=da39a3ee5e6b4b0d input=124b58387c158179]*/ 227db96d56Sopenharmony_ci 237db96d56Sopenharmony_ci#include "clinic/fcntlmodule.c.h" 247db96d56Sopenharmony_ci 257db96d56Sopenharmony_ci/*[clinic input] 267db96d56Sopenharmony_cifcntl.fcntl 277db96d56Sopenharmony_ci 287db96d56Sopenharmony_ci fd: fildes 297db96d56Sopenharmony_ci cmd as code: int 307db96d56Sopenharmony_ci arg: object(c_default='NULL') = 0 317db96d56Sopenharmony_ci / 327db96d56Sopenharmony_ci 337db96d56Sopenharmony_ciPerform the operation `cmd` on file descriptor fd. 347db96d56Sopenharmony_ci 357db96d56Sopenharmony_ciThe values used for `cmd` are operating system dependent, and are available 367db96d56Sopenharmony_cias constants in the fcntl module, using the same names as used in 377db96d56Sopenharmony_cithe relevant C header files. The argument arg is optional, and 387db96d56Sopenharmony_cidefaults to 0; it may be an int or a string. If arg is given as a string, 397db96d56Sopenharmony_cithe return value of fcntl is a string of that length, containing the 407db96d56Sopenharmony_ciresulting value put in the arg buffer by the operating system. The length 417db96d56Sopenharmony_ciof the arg string is not allowed to exceed 1024 bytes. If the arg given 427db96d56Sopenharmony_ciis an integer or if none is specified, the result value is an integer 437db96d56Sopenharmony_cicorresponding to the return value of the fcntl call in the C code. 447db96d56Sopenharmony_ci[clinic start generated code]*/ 457db96d56Sopenharmony_ci 467db96d56Sopenharmony_cistatic PyObject * 477db96d56Sopenharmony_cifcntl_fcntl_impl(PyObject *module, int fd, int code, PyObject *arg) 487db96d56Sopenharmony_ci/*[clinic end generated code: output=888fc93b51c295bd input=7955340198e5f334]*/ 497db96d56Sopenharmony_ci{ 507db96d56Sopenharmony_ci unsigned int int_arg = 0; 517db96d56Sopenharmony_ci int ret; 527db96d56Sopenharmony_ci char *str; 537db96d56Sopenharmony_ci Py_ssize_t len; 547db96d56Sopenharmony_ci char buf[1024]; 557db96d56Sopenharmony_ci int async_err = 0; 567db96d56Sopenharmony_ci 577db96d56Sopenharmony_ci if (PySys_Audit("fcntl.fcntl", "iiO", fd, code, arg ? arg : Py_None) < 0) { 587db96d56Sopenharmony_ci return NULL; 597db96d56Sopenharmony_ci } 607db96d56Sopenharmony_ci 617db96d56Sopenharmony_ci if (arg != NULL) { 627db96d56Sopenharmony_ci int parse_result; 637db96d56Sopenharmony_ci 647db96d56Sopenharmony_ci if (PyArg_Parse(arg, "s#", &str, &len)) { 657db96d56Sopenharmony_ci if ((size_t)len > sizeof buf) { 667db96d56Sopenharmony_ci PyErr_SetString(PyExc_ValueError, 677db96d56Sopenharmony_ci "fcntl string arg too long"); 687db96d56Sopenharmony_ci return NULL; 697db96d56Sopenharmony_ci } 707db96d56Sopenharmony_ci memcpy(buf, str, len); 717db96d56Sopenharmony_ci do { 727db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS 737db96d56Sopenharmony_ci ret = fcntl(fd, code, buf); 747db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 757db96d56Sopenharmony_ci } while (ret == -1 && errno == EINTR && !(async_err = PyErr_CheckSignals())); 767db96d56Sopenharmony_ci if (ret < 0) { 777db96d56Sopenharmony_ci return !async_err ? PyErr_SetFromErrno(PyExc_OSError) : NULL; 787db96d56Sopenharmony_ci } 797db96d56Sopenharmony_ci return PyBytes_FromStringAndSize(buf, len); 807db96d56Sopenharmony_ci } 817db96d56Sopenharmony_ci 827db96d56Sopenharmony_ci PyErr_Clear(); 837db96d56Sopenharmony_ci parse_result = PyArg_Parse(arg, 847db96d56Sopenharmony_ci "I;fcntl requires a file or file descriptor," 857db96d56Sopenharmony_ci " an integer and optionally a third integer or a string", 867db96d56Sopenharmony_ci &int_arg); 877db96d56Sopenharmony_ci if (!parse_result) { 887db96d56Sopenharmony_ci return NULL; 897db96d56Sopenharmony_ci } 907db96d56Sopenharmony_ci } 917db96d56Sopenharmony_ci 927db96d56Sopenharmony_ci do { 937db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS 947db96d56Sopenharmony_ci ret = fcntl(fd, code, (int)int_arg); 957db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 967db96d56Sopenharmony_ci } while (ret == -1 && errno == EINTR && !(async_err = PyErr_CheckSignals())); 977db96d56Sopenharmony_ci if (ret < 0) { 987db96d56Sopenharmony_ci return !async_err ? PyErr_SetFromErrno(PyExc_OSError) : NULL; 997db96d56Sopenharmony_ci } 1007db96d56Sopenharmony_ci return PyLong_FromLong((long)ret); 1017db96d56Sopenharmony_ci} 1027db96d56Sopenharmony_ci 1037db96d56Sopenharmony_ci 1047db96d56Sopenharmony_ci/*[clinic input] 1057db96d56Sopenharmony_cifcntl.ioctl 1067db96d56Sopenharmony_ci 1077db96d56Sopenharmony_ci fd: fildes 1087db96d56Sopenharmony_ci request as code: unsigned_int(bitwise=True) 1097db96d56Sopenharmony_ci arg as ob_arg: object(c_default='NULL') = 0 1107db96d56Sopenharmony_ci mutate_flag as mutate_arg: bool = True 1117db96d56Sopenharmony_ci / 1127db96d56Sopenharmony_ci 1137db96d56Sopenharmony_ciPerform the operation `request` on file descriptor `fd`. 1147db96d56Sopenharmony_ci 1157db96d56Sopenharmony_ciThe values used for `request` are operating system dependent, and are available 1167db96d56Sopenharmony_cias constants in the fcntl or termios library modules, using the same names as 1177db96d56Sopenharmony_ciused in the relevant C header files. 1187db96d56Sopenharmony_ci 1197db96d56Sopenharmony_ciThe argument `arg` is optional, and defaults to 0; it may be an int or a 1207db96d56Sopenharmony_cibuffer containing character data (most likely a string or an array). 1217db96d56Sopenharmony_ci 1227db96d56Sopenharmony_ciIf the argument is a mutable buffer (such as an array) and if the 1237db96d56Sopenharmony_cimutate_flag argument (which is only allowed in this case) is true then the 1247db96d56Sopenharmony_cibuffer is (in effect) passed to the operating system and changes made by 1257db96d56Sopenharmony_cithe OS will be reflected in the contents of the buffer after the call has 1267db96d56Sopenharmony_cireturned. The return value is the integer returned by the ioctl system 1277db96d56Sopenharmony_cicall. 1287db96d56Sopenharmony_ci 1297db96d56Sopenharmony_ciIf the argument is a mutable buffer and the mutable_flag argument is false, 1307db96d56Sopenharmony_cithe behavior is as if a string had been passed. 1317db96d56Sopenharmony_ci 1327db96d56Sopenharmony_ciIf the argument is an immutable buffer (most likely a string) then a copy 1337db96d56Sopenharmony_ciof the buffer is passed to the operating system and the return value is a 1347db96d56Sopenharmony_cistring of the same length containing whatever the operating system put in 1357db96d56Sopenharmony_cithe buffer. The length of the arg buffer in this case is not allowed to 1367db96d56Sopenharmony_ciexceed 1024 bytes. 1377db96d56Sopenharmony_ci 1387db96d56Sopenharmony_ciIf the arg given is an integer or if none is specified, the result value is 1397db96d56Sopenharmony_cian integer corresponding to the return value of the ioctl call in the C 1407db96d56Sopenharmony_cicode. 1417db96d56Sopenharmony_ci[clinic start generated code]*/ 1427db96d56Sopenharmony_ci 1437db96d56Sopenharmony_cistatic PyObject * 1447db96d56Sopenharmony_cifcntl_ioctl_impl(PyObject *module, int fd, unsigned int code, 1457db96d56Sopenharmony_ci PyObject *ob_arg, int mutate_arg) 1467db96d56Sopenharmony_ci/*[clinic end generated code: output=7f7f5840c65991be input=967b4a4cbeceb0a8]*/ 1477db96d56Sopenharmony_ci{ 1487db96d56Sopenharmony_ci#define IOCTL_BUFSZ 1024 1497db96d56Sopenharmony_ci /* We use the unsigned non-checked 'I' format for the 'code' parameter 1507db96d56Sopenharmony_ci because the system expects it to be a 32bit bit field value 1517db96d56Sopenharmony_ci regardless of it being passed as an int or unsigned long on 1527db96d56Sopenharmony_ci various platforms. See the termios.TIOCSWINSZ constant across 1537db96d56Sopenharmony_ci platforms for an example of this. 1547db96d56Sopenharmony_ci 1557db96d56Sopenharmony_ci If any of the 64bit platforms ever decide to use more than 32bits 1567db96d56Sopenharmony_ci in their unsigned long ioctl codes this will break and need 1577db96d56Sopenharmony_ci special casing based on the platform being built on. 1587db96d56Sopenharmony_ci */ 1597db96d56Sopenharmony_ci int arg = 0; 1607db96d56Sopenharmony_ci int ret; 1617db96d56Sopenharmony_ci Py_buffer pstr; 1627db96d56Sopenharmony_ci char *str; 1637db96d56Sopenharmony_ci Py_ssize_t len; 1647db96d56Sopenharmony_ci char buf[IOCTL_BUFSZ+1]; /* argument plus NUL byte */ 1657db96d56Sopenharmony_ci 1667db96d56Sopenharmony_ci if (PySys_Audit("fcntl.ioctl", "iIO", fd, code, 1677db96d56Sopenharmony_ci ob_arg ? ob_arg : Py_None) < 0) { 1687db96d56Sopenharmony_ci return NULL; 1697db96d56Sopenharmony_ci } 1707db96d56Sopenharmony_ci 1717db96d56Sopenharmony_ci if (ob_arg != NULL) { 1727db96d56Sopenharmony_ci if (PyArg_Parse(ob_arg, "w*:ioctl", &pstr)) { 1737db96d56Sopenharmony_ci char *arg; 1747db96d56Sopenharmony_ci str = pstr.buf; 1757db96d56Sopenharmony_ci len = pstr.len; 1767db96d56Sopenharmony_ci 1777db96d56Sopenharmony_ci if (mutate_arg) { 1787db96d56Sopenharmony_ci if (len <= IOCTL_BUFSZ) { 1797db96d56Sopenharmony_ci memcpy(buf, str, len); 1807db96d56Sopenharmony_ci buf[len] = '\0'; 1817db96d56Sopenharmony_ci arg = buf; 1827db96d56Sopenharmony_ci } 1837db96d56Sopenharmony_ci else { 1847db96d56Sopenharmony_ci arg = str; 1857db96d56Sopenharmony_ci } 1867db96d56Sopenharmony_ci } 1877db96d56Sopenharmony_ci else { 1887db96d56Sopenharmony_ci if (len > IOCTL_BUFSZ) { 1897db96d56Sopenharmony_ci PyBuffer_Release(&pstr); 1907db96d56Sopenharmony_ci PyErr_SetString(PyExc_ValueError, 1917db96d56Sopenharmony_ci "ioctl string arg too long"); 1927db96d56Sopenharmony_ci return NULL; 1937db96d56Sopenharmony_ci } 1947db96d56Sopenharmony_ci else { 1957db96d56Sopenharmony_ci memcpy(buf, str, len); 1967db96d56Sopenharmony_ci buf[len] = '\0'; 1977db96d56Sopenharmony_ci arg = buf; 1987db96d56Sopenharmony_ci } 1997db96d56Sopenharmony_ci } 2007db96d56Sopenharmony_ci if (buf == arg) { 2017db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS /* think array.resize() */ 2027db96d56Sopenharmony_ci ret = ioctl(fd, code, arg); 2037db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 2047db96d56Sopenharmony_ci } 2057db96d56Sopenharmony_ci else { 2067db96d56Sopenharmony_ci ret = ioctl(fd, code, arg); 2077db96d56Sopenharmony_ci } 2087db96d56Sopenharmony_ci if (mutate_arg && (len <= IOCTL_BUFSZ)) { 2097db96d56Sopenharmony_ci memcpy(str, buf, len); 2107db96d56Sopenharmony_ci } 2117db96d56Sopenharmony_ci PyBuffer_Release(&pstr); /* No further access to str below this point */ 2127db96d56Sopenharmony_ci if (ret < 0) { 2137db96d56Sopenharmony_ci PyErr_SetFromErrno(PyExc_OSError); 2147db96d56Sopenharmony_ci return NULL; 2157db96d56Sopenharmony_ci } 2167db96d56Sopenharmony_ci if (mutate_arg) { 2177db96d56Sopenharmony_ci return PyLong_FromLong(ret); 2187db96d56Sopenharmony_ci } 2197db96d56Sopenharmony_ci else { 2207db96d56Sopenharmony_ci return PyBytes_FromStringAndSize(buf, len); 2217db96d56Sopenharmony_ci } 2227db96d56Sopenharmony_ci } 2237db96d56Sopenharmony_ci 2247db96d56Sopenharmony_ci PyErr_Clear(); 2257db96d56Sopenharmony_ci if (PyArg_Parse(ob_arg, "s*:ioctl", &pstr)) { 2267db96d56Sopenharmony_ci str = pstr.buf; 2277db96d56Sopenharmony_ci len = pstr.len; 2287db96d56Sopenharmony_ci if (len > IOCTL_BUFSZ) { 2297db96d56Sopenharmony_ci PyBuffer_Release(&pstr); 2307db96d56Sopenharmony_ci PyErr_SetString(PyExc_ValueError, 2317db96d56Sopenharmony_ci "ioctl string arg too long"); 2327db96d56Sopenharmony_ci return NULL; 2337db96d56Sopenharmony_ci } 2347db96d56Sopenharmony_ci memcpy(buf, str, len); 2357db96d56Sopenharmony_ci buf[len] = '\0'; 2367db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS 2377db96d56Sopenharmony_ci ret = ioctl(fd, code, buf); 2387db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 2397db96d56Sopenharmony_ci if (ret < 0) { 2407db96d56Sopenharmony_ci PyBuffer_Release(&pstr); 2417db96d56Sopenharmony_ci PyErr_SetFromErrno(PyExc_OSError); 2427db96d56Sopenharmony_ci return NULL; 2437db96d56Sopenharmony_ci } 2447db96d56Sopenharmony_ci PyBuffer_Release(&pstr); 2457db96d56Sopenharmony_ci return PyBytes_FromStringAndSize(buf, len); 2467db96d56Sopenharmony_ci } 2477db96d56Sopenharmony_ci 2487db96d56Sopenharmony_ci PyErr_Clear(); 2497db96d56Sopenharmony_ci if (!PyArg_Parse(ob_arg, 2507db96d56Sopenharmony_ci "i;ioctl requires a file or file descriptor," 2517db96d56Sopenharmony_ci " an integer and optionally an integer or buffer argument", 2527db96d56Sopenharmony_ci &arg)) { 2537db96d56Sopenharmony_ci return NULL; 2547db96d56Sopenharmony_ci } 2557db96d56Sopenharmony_ci // Fall-through to outside the 'if' statement. 2567db96d56Sopenharmony_ci } 2577db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS 2587db96d56Sopenharmony_ci ret = ioctl(fd, code, arg); 2597db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 2607db96d56Sopenharmony_ci if (ret < 0) { 2617db96d56Sopenharmony_ci PyErr_SetFromErrno(PyExc_OSError); 2627db96d56Sopenharmony_ci return NULL; 2637db96d56Sopenharmony_ci } 2647db96d56Sopenharmony_ci return PyLong_FromLong((long)ret); 2657db96d56Sopenharmony_ci#undef IOCTL_BUFSZ 2667db96d56Sopenharmony_ci} 2677db96d56Sopenharmony_ci 2687db96d56Sopenharmony_ci/*[clinic input] 2697db96d56Sopenharmony_cifcntl.flock 2707db96d56Sopenharmony_ci 2717db96d56Sopenharmony_ci fd: fildes 2727db96d56Sopenharmony_ci operation as code: int 2737db96d56Sopenharmony_ci / 2747db96d56Sopenharmony_ci 2757db96d56Sopenharmony_ciPerform the lock operation `operation` on file descriptor `fd`. 2767db96d56Sopenharmony_ci 2777db96d56Sopenharmony_ciSee the Unix manual page for flock(2) for details (On some systems, this 2787db96d56Sopenharmony_cifunction is emulated using fcntl()). 2797db96d56Sopenharmony_ci[clinic start generated code]*/ 2807db96d56Sopenharmony_ci 2817db96d56Sopenharmony_cistatic PyObject * 2827db96d56Sopenharmony_cifcntl_flock_impl(PyObject *module, int fd, int code) 2837db96d56Sopenharmony_ci/*[clinic end generated code: output=84059e2b37d2fc64 input=0bfc00f795953452]*/ 2847db96d56Sopenharmony_ci{ 2857db96d56Sopenharmony_ci int ret; 2867db96d56Sopenharmony_ci int async_err = 0; 2877db96d56Sopenharmony_ci 2887db96d56Sopenharmony_ci if (PySys_Audit("fcntl.flock", "ii", fd, code) < 0) { 2897db96d56Sopenharmony_ci return NULL; 2907db96d56Sopenharmony_ci } 2917db96d56Sopenharmony_ci 2927db96d56Sopenharmony_ci#ifdef HAVE_FLOCK 2937db96d56Sopenharmony_ci do { 2947db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS 2957db96d56Sopenharmony_ci ret = flock(fd, code); 2967db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 2977db96d56Sopenharmony_ci } while (ret == -1 && errno == EINTR && !(async_err = PyErr_CheckSignals())); 2987db96d56Sopenharmony_ci#else 2997db96d56Sopenharmony_ci 3007db96d56Sopenharmony_ci#ifndef LOCK_SH 3017db96d56Sopenharmony_ci#define LOCK_SH 1 /* shared lock */ 3027db96d56Sopenharmony_ci#define LOCK_EX 2 /* exclusive lock */ 3037db96d56Sopenharmony_ci#define LOCK_NB 4 /* don't block when locking */ 3047db96d56Sopenharmony_ci#define LOCK_UN 8 /* unlock */ 3057db96d56Sopenharmony_ci#endif 3067db96d56Sopenharmony_ci { 3077db96d56Sopenharmony_ci struct flock l; 3087db96d56Sopenharmony_ci if (code == LOCK_UN) 3097db96d56Sopenharmony_ci l.l_type = F_UNLCK; 3107db96d56Sopenharmony_ci else if (code & LOCK_SH) 3117db96d56Sopenharmony_ci l.l_type = F_RDLCK; 3127db96d56Sopenharmony_ci else if (code & LOCK_EX) 3137db96d56Sopenharmony_ci l.l_type = F_WRLCK; 3147db96d56Sopenharmony_ci else { 3157db96d56Sopenharmony_ci PyErr_SetString(PyExc_ValueError, 3167db96d56Sopenharmony_ci "unrecognized flock argument"); 3177db96d56Sopenharmony_ci return NULL; 3187db96d56Sopenharmony_ci } 3197db96d56Sopenharmony_ci l.l_whence = l.l_start = l.l_len = 0; 3207db96d56Sopenharmony_ci do { 3217db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS 3227db96d56Sopenharmony_ci ret = fcntl(fd, (code & LOCK_NB) ? F_SETLK : F_SETLKW, &l); 3237db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 3247db96d56Sopenharmony_ci } while (ret == -1 && errno == EINTR && !(async_err = PyErr_CheckSignals())); 3257db96d56Sopenharmony_ci } 3267db96d56Sopenharmony_ci#endif /* HAVE_FLOCK */ 3277db96d56Sopenharmony_ci if (ret < 0) { 3287db96d56Sopenharmony_ci return !async_err ? PyErr_SetFromErrno(PyExc_OSError) : NULL; 3297db96d56Sopenharmony_ci } 3307db96d56Sopenharmony_ci Py_RETURN_NONE; 3317db96d56Sopenharmony_ci} 3327db96d56Sopenharmony_ci 3337db96d56Sopenharmony_ci 3347db96d56Sopenharmony_ci/*[clinic input] 3357db96d56Sopenharmony_cifcntl.lockf 3367db96d56Sopenharmony_ci 3377db96d56Sopenharmony_ci fd: fildes 3387db96d56Sopenharmony_ci cmd as code: int 3397db96d56Sopenharmony_ci len as lenobj: object(c_default='NULL') = 0 3407db96d56Sopenharmony_ci start as startobj: object(c_default='NULL') = 0 3417db96d56Sopenharmony_ci whence: int = 0 3427db96d56Sopenharmony_ci / 3437db96d56Sopenharmony_ci 3447db96d56Sopenharmony_ciA wrapper around the fcntl() locking calls. 3457db96d56Sopenharmony_ci 3467db96d56Sopenharmony_ci`fd` is the file descriptor of the file to lock or unlock, and operation is one 3477db96d56Sopenharmony_ciof the following values: 3487db96d56Sopenharmony_ci 3497db96d56Sopenharmony_ci LOCK_UN - unlock 3507db96d56Sopenharmony_ci LOCK_SH - acquire a shared lock 3517db96d56Sopenharmony_ci LOCK_EX - acquire an exclusive lock 3527db96d56Sopenharmony_ci 3537db96d56Sopenharmony_ciWhen operation is LOCK_SH or LOCK_EX, it can also be bitwise ORed with 3547db96d56Sopenharmony_ciLOCK_NB to avoid blocking on lock acquisition. If LOCK_NB is used and the 3557db96d56Sopenharmony_cilock cannot be acquired, an OSError will be raised and the exception will 3567db96d56Sopenharmony_cihave an errno attribute set to EACCES or EAGAIN (depending on the operating 3577db96d56Sopenharmony_cisystem -- for portability, check for either value). 3587db96d56Sopenharmony_ci 3597db96d56Sopenharmony_ci`len` is the number of bytes to lock, with the default meaning to lock to 3607db96d56Sopenharmony_ciEOF. `start` is the byte offset, relative to `whence`, to that the lock 3617db96d56Sopenharmony_cistarts. `whence` is as with fileobj.seek(), specifically: 3627db96d56Sopenharmony_ci 3637db96d56Sopenharmony_ci 0 - relative to the start of the file (SEEK_SET) 3647db96d56Sopenharmony_ci 1 - relative to the current buffer position (SEEK_CUR) 3657db96d56Sopenharmony_ci 2 - relative to the end of the file (SEEK_END) 3667db96d56Sopenharmony_ci[clinic start generated code]*/ 3677db96d56Sopenharmony_ci 3687db96d56Sopenharmony_cistatic PyObject * 3697db96d56Sopenharmony_cifcntl_lockf_impl(PyObject *module, int fd, int code, PyObject *lenobj, 3707db96d56Sopenharmony_ci PyObject *startobj, int whence) 3717db96d56Sopenharmony_ci/*[clinic end generated code: output=4985e7a172e7461a input=5480479fc63a04b8]*/ 3727db96d56Sopenharmony_ci{ 3737db96d56Sopenharmony_ci int ret; 3747db96d56Sopenharmony_ci int async_err = 0; 3757db96d56Sopenharmony_ci 3767db96d56Sopenharmony_ci if (PySys_Audit("fcntl.lockf", "iiOOi", fd, code, lenobj ? lenobj : Py_None, 3777db96d56Sopenharmony_ci startobj ? startobj : Py_None, whence) < 0) { 3787db96d56Sopenharmony_ci return NULL; 3797db96d56Sopenharmony_ci } 3807db96d56Sopenharmony_ci 3817db96d56Sopenharmony_ci#ifndef LOCK_SH 3827db96d56Sopenharmony_ci#define LOCK_SH 1 /* shared lock */ 3837db96d56Sopenharmony_ci#define LOCK_EX 2 /* exclusive lock */ 3847db96d56Sopenharmony_ci#define LOCK_NB 4 /* don't block when locking */ 3857db96d56Sopenharmony_ci#define LOCK_UN 8 /* unlock */ 3867db96d56Sopenharmony_ci#endif /* LOCK_SH */ 3877db96d56Sopenharmony_ci { 3887db96d56Sopenharmony_ci struct flock l; 3897db96d56Sopenharmony_ci if (code == LOCK_UN) 3907db96d56Sopenharmony_ci l.l_type = F_UNLCK; 3917db96d56Sopenharmony_ci else if (code & LOCK_SH) 3927db96d56Sopenharmony_ci l.l_type = F_RDLCK; 3937db96d56Sopenharmony_ci else if (code & LOCK_EX) 3947db96d56Sopenharmony_ci l.l_type = F_WRLCK; 3957db96d56Sopenharmony_ci else { 3967db96d56Sopenharmony_ci PyErr_SetString(PyExc_ValueError, 3977db96d56Sopenharmony_ci "unrecognized lockf argument"); 3987db96d56Sopenharmony_ci return NULL; 3997db96d56Sopenharmony_ci } 4007db96d56Sopenharmony_ci l.l_start = l.l_len = 0; 4017db96d56Sopenharmony_ci if (startobj != NULL) { 4027db96d56Sopenharmony_ci#if !defined(HAVE_LARGEFILE_SUPPORT) 4037db96d56Sopenharmony_ci l.l_start = PyLong_AsLong(startobj); 4047db96d56Sopenharmony_ci#else 4057db96d56Sopenharmony_ci l.l_start = PyLong_Check(startobj) ? 4067db96d56Sopenharmony_ci PyLong_AsLongLong(startobj) : 4077db96d56Sopenharmony_ci PyLong_AsLong(startobj); 4087db96d56Sopenharmony_ci#endif 4097db96d56Sopenharmony_ci if (PyErr_Occurred()) 4107db96d56Sopenharmony_ci return NULL; 4117db96d56Sopenharmony_ci } 4127db96d56Sopenharmony_ci if (lenobj != NULL) { 4137db96d56Sopenharmony_ci#if !defined(HAVE_LARGEFILE_SUPPORT) 4147db96d56Sopenharmony_ci l.l_len = PyLong_AsLong(lenobj); 4157db96d56Sopenharmony_ci#else 4167db96d56Sopenharmony_ci l.l_len = PyLong_Check(lenobj) ? 4177db96d56Sopenharmony_ci PyLong_AsLongLong(lenobj) : 4187db96d56Sopenharmony_ci PyLong_AsLong(lenobj); 4197db96d56Sopenharmony_ci#endif 4207db96d56Sopenharmony_ci if (PyErr_Occurred()) 4217db96d56Sopenharmony_ci return NULL; 4227db96d56Sopenharmony_ci } 4237db96d56Sopenharmony_ci l.l_whence = whence; 4247db96d56Sopenharmony_ci do { 4257db96d56Sopenharmony_ci Py_BEGIN_ALLOW_THREADS 4267db96d56Sopenharmony_ci ret = fcntl(fd, (code & LOCK_NB) ? F_SETLK : F_SETLKW, &l); 4277db96d56Sopenharmony_ci Py_END_ALLOW_THREADS 4287db96d56Sopenharmony_ci } while (ret == -1 && errno == EINTR && !(async_err = PyErr_CheckSignals())); 4297db96d56Sopenharmony_ci } 4307db96d56Sopenharmony_ci if (ret < 0) { 4317db96d56Sopenharmony_ci return !async_err ? PyErr_SetFromErrno(PyExc_OSError) : NULL; 4327db96d56Sopenharmony_ci } 4337db96d56Sopenharmony_ci Py_RETURN_NONE; 4347db96d56Sopenharmony_ci} 4357db96d56Sopenharmony_ci 4367db96d56Sopenharmony_ci/* List of functions */ 4377db96d56Sopenharmony_ci 4387db96d56Sopenharmony_cistatic PyMethodDef fcntl_methods[] = { 4397db96d56Sopenharmony_ci FCNTL_FCNTL_METHODDEF 4407db96d56Sopenharmony_ci FCNTL_IOCTL_METHODDEF 4417db96d56Sopenharmony_ci FCNTL_FLOCK_METHODDEF 4427db96d56Sopenharmony_ci FCNTL_LOCKF_METHODDEF 4437db96d56Sopenharmony_ci {NULL, NULL} /* sentinel */ 4447db96d56Sopenharmony_ci}; 4457db96d56Sopenharmony_ci 4467db96d56Sopenharmony_ci 4477db96d56Sopenharmony_ciPyDoc_STRVAR(module_doc, 4487db96d56Sopenharmony_ci"This module performs file control and I/O control on file\n\ 4497db96d56Sopenharmony_cidescriptors. It is an interface to the fcntl() and ioctl() Unix\n\ 4507db96d56Sopenharmony_ciroutines. File descriptors can be obtained with the fileno() method of\n\ 4517db96d56Sopenharmony_cia file or socket object."); 4527db96d56Sopenharmony_ci 4537db96d56Sopenharmony_ci/* Module initialisation */ 4547db96d56Sopenharmony_ci 4557db96d56Sopenharmony_ci 4567db96d56Sopenharmony_cistatic int 4577db96d56Sopenharmony_ciall_ins(PyObject* m) 4587db96d56Sopenharmony_ci{ 4597db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_SH)) return -1; 4607db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_EX)) return -1; 4617db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_NB)) return -1; 4627db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_UN)) return -1; 4637db96d56Sopenharmony_ci/* GNU extensions, as of glibc 2.2.4 */ 4647db96d56Sopenharmony_ci#ifdef LOCK_MAND 4657db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_MAND)) return -1; 4667db96d56Sopenharmony_ci#endif 4677db96d56Sopenharmony_ci#ifdef LOCK_READ 4687db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_READ)) return -1; 4697db96d56Sopenharmony_ci#endif 4707db96d56Sopenharmony_ci#ifdef LOCK_WRITE 4717db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_WRITE)) return -1; 4727db96d56Sopenharmony_ci#endif 4737db96d56Sopenharmony_ci#ifdef LOCK_RW 4747db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, LOCK_RW)) return -1; 4757db96d56Sopenharmony_ci#endif 4767db96d56Sopenharmony_ci 4777db96d56Sopenharmony_ci#ifdef F_DUPFD 4787db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_DUPFD)) return -1; 4797db96d56Sopenharmony_ci#endif 4807db96d56Sopenharmony_ci#ifdef F_DUPFD_CLOEXEC 4817db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_DUPFD_CLOEXEC)) return -1; 4827db96d56Sopenharmony_ci#endif 4837db96d56Sopenharmony_ci#ifdef F_GETFD 4847db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETFD)) return -1; 4857db96d56Sopenharmony_ci#endif 4867db96d56Sopenharmony_ci#ifdef F_SETFD 4877db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETFD)) return -1; 4887db96d56Sopenharmony_ci#endif 4897db96d56Sopenharmony_ci#ifdef F_GETFL 4907db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETFL)) return -1; 4917db96d56Sopenharmony_ci#endif 4927db96d56Sopenharmony_ci#ifdef F_SETFL 4937db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETFL)) return -1; 4947db96d56Sopenharmony_ci#endif 4957db96d56Sopenharmony_ci#ifdef F_GETLK 4967db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETLK)) return -1; 4977db96d56Sopenharmony_ci#endif 4987db96d56Sopenharmony_ci#ifdef F_SETLK 4997db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETLK)) return -1; 5007db96d56Sopenharmony_ci#endif 5017db96d56Sopenharmony_ci#ifdef F_SETLKW 5027db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETLKW)) return -1; 5037db96d56Sopenharmony_ci#endif 5047db96d56Sopenharmony_ci#ifdef F_OFD_GETLK 5057db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_OFD_GETLK)) return -1; 5067db96d56Sopenharmony_ci#endif 5077db96d56Sopenharmony_ci#ifdef F_OFD_SETLK 5087db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_OFD_SETLK)) return -1; 5097db96d56Sopenharmony_ci#endif 5107db96d56Sopenharmony_ci#ifdef F_OFD_SETLKW 5117db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_OFD_SETLKW)) return -1; 5127db96d56Sopenharmony_ci#endif 5137db96d56Sopenharmony_ci#ifdef F_GETOWN 5147db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETOWN)) return -1; 5157db96d56Sopenharmony_ci#endif 5167db96d56Sopenharmony_ci#ifdef F_SETOWN 5177db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETOWN)) return -1; 5187db96d56Sopenharmony_ci#endif 5197db96d56Sopenharmony_ci#ifdef F_GETPATH 5207db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETPATH)) return -1; 5217db96d56Sopenharmony_ci#endif 5227db96d56Sopenharmony_ci#ifdef F_GETSIG 5237db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETSIG)) return -1; 5247db96d56Sopenharmony_ci#endif 5257db96d56Sopenharmony_ci#ifdef F_SETSIG 5267db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETSIG)) return -1; 5277db96d56Sopenharmony_ci#endif 5287db96d56Sopenharmony_ci#ifdef F_RDLCK 5297db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_RDLCK)) return -1; 5307db96d56Sopenharmony_ci#endif 5317db96d56Sopenharmony_ci#ifdef F_WRLCK 5327db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_WRLCK)) return -1; 5337db96d56Sopenharmony_ci#endif 5347db96d56Sopenharmony_ci#ifdef F_UNLCK 5357db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_UNLCK)) return -1; 5367db96d56Sopenharmony_ci#endif 5377db96d56Sopenharmony_ci/* LFS constants */ 5387db96d56Sopenharmony_ci#ifdef F_GETLK64 5397db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETLK64)) return -1; 5407db96d56Sopenharmony_ci#endif 5417db96d56Sopenharmony_ci#ifdef F_SETLK64 5427db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETLK64)) return -1; 5437db96d56Sopenharmony_ci#endif 5447db96d56Sopenharmony_ci#ifdef F_SETLKW64 5457db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETLKW64)) return -1; 5467db96d56Sopenharmony_ci#endif 5477db96d56Sopenharmony_ci/* GNU extensions, as of glibc 2.2.4. */ 5487db96d56Sopenharmony_ci#ifdef FASYNC 5497db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, FASYNC)) return -1; 5507db96d56Sopenharmony_ci#endif 5517db96d56Sopenharmony_ci#ifdef F_SETLEASE 5527db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETLEASE)) return -1; 5537db96d56Sopenharmony_ci#endif 5547db96d56Sopenharmony_ci#ifdef F_GETLEASE 5557db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETLEASE)) return -1; 5567db96d56Sopenharmony_ci#endif 5577db96d56Sopenharmony_ci#ifdef F_NOTIFY 5587db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_NOTIFY)) return -1; 5597db96d56Sopenharmony_ci#endif 5607db96d56Sopenharmony_ci/* Old BSD flock(). */ 5617db96d56Sopenharmony_ci#ifdef F_EXLCK 5627db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_EXLCK)) return -1; 5637db96d56Sopenharmony_ci#endif 5647db96d56Sopenharmony_ci#ifdef F_SHLCK 5657db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SHLCK)) return -1; 5667db96d56Sopenharmony_ci#endif 5677db96d56Sopenharmony_ci 5687db96d56Sopenharmony_ci/* Linux specifics */ 5697db96d56Sopenharmony_ci#ifdef F_SETPIPE_SZ 5707db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SETPIPE_SZ)) return -1; 5717db96d56Sopenharmony_ci#endif 5727db96d56Sopenharmony_ci#ifdef F_GETPIPE_SZ 5737db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GETPIPE_SZ)) return -1; 5747db96d56Sopenharmony_ci#endif 5757db96d56Sopenharmony_ci 5767db96d56Sopenharmony_ci/* OS X specifics */ 5777db96d56Sopenharmony_ci#ifdef F_FULLFSYNC 5787db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_FULLFSYNC)) return -1; 5797db96d56Sopenharmony_ci#endif 5807db96d56Sopenharmony_ci#ifdef F_NOCACHE 5817db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_NOCACHE)) return -1; 5827db96d56Sopenharmony_ci#endif 5837db96d56Sopenharmony_ci 5847db96d56Sopenharmony_ci/* FreeBSD specifics */ 5857db96d56Sopenharmony_ci#ifdef F_DUP2FD 5867db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_DUP2FD)) return -1; 5877db96d56Sopenharmony_ci#endif 5887db96d56Sopenharmony_ci#ifdef F_DUP2FD_CLOEXEC 5897db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_DUP2FD_CLOEXEC)) return -1; 5907db96d56Sopenharmony_ci#endif 5917db96d56Sopenharmony_ci 5927db96d56Sopenharmony_ci/* For F_{GET|SET}FL */ 5937db96d56Sopenharmony_ci#ifdef FD_CLOEXEC 5947db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, FD_CLOEXEC)) return -1; 5957db96d56Sopenharmony_ci#endif 5967db96d56Sopenharmony_ci 5977db96d56Sopenharmony_ci/* For F_NOTIFY */ 5987db96d56Sopenharmony_ci#ifdef DN_ACCESS 5997db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, DN_ACCESS)) return -1; 6007db96d56Sopenharmony_ci#endif 6017db96d56Sopenharmony_ci#ifdef DN_MODIFY 6027db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, DN_MODIFY)) return -1; 6037db96d56Sopenharmony_ci#endif 6047db96d56Sopenharmony_ci#ifdef DN_CREATE 6057db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, DN_CREATE)) return -1; 6067db96d56Sopenharmony_ci#endif 6077db96d56Sopenharmony_ci#ifdef DN_DELETE 6087db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, DN_DELETE)) return -1; 6097db96d56Sopenharmony_ci#endif 6107db96d56Sopenharmony_ci#ifdef DN_RENAME 6117db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, DN_RENAME)) return -1; 6127db96d56Sopenharmony_ci#endif 6137db96d56Sopenharmony_ci#ifdef DN_ATTRIB 6147db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, DN_ATTRIB)) return -1; 6157db96d56Sopenharmony_ci#endif 6167db96d56Sopenharmony_ci#ifdef DN_MULTISHOT 6177db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, DN_MULTISHOT)) return -1; 6187db96d56Sopenharmony_ci#endif 6197db96d56Sopenharmony_ci 6207db96d56Sopenharmony_ci#ifdef HAVE_STROPTS_H 6217db96d56Sopenharmony_ci /* Unix 98 guarantees that these are in stropts.h. */ 6227db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_PUSH)) return -1; 6237db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_POP)) return -1; 6247db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_LOOK)) return -1; 6257db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_FLUSH)) return -1; 6267db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_FLUSHBAND)) return -1; 6277db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_SETSIG)) return -1; 6287db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_GETSIG)) return -1; 6297db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_FIND)) return -1; 6307db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_PEEK)) return -1; 6317db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_SRDOPT)) return -1; 6327db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_GRDOPT)) return -1; 6337db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_NREAD)) return -1; 6347db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_FDINSERT)) return -1; 6357db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_STR)) return -1; 6367db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_SWROPT)) return -1; 6377db96d56Sopenharmony_ci#ifdef I_GWROPT 6387db96d56Sopenharmony_ci /* despite the comment above, old-ish glibcs miss a couple... */ 6397db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_GWROPT)) return -1; 6407db96d56Sopenharmony_ci#endif 6417db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_SENDFD)) return -1; 6427db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_RECVFD)) return -1; 6437db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_LIST)) return -1; 6447db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_ATMARK)) return -1; 6457db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_CKBAND)) return -1; 6467db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_GETBAND)) return -1; 6477db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_CANPUT)) return -1; 6487db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_SETCLTIME)) return -1; 6497db96d56Sopenharmony_ci#ifdef I_GETCLTIME 6507db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_GETCLTIME)) return -1; 6517db96d56Sopenharmony_ci#endif 6527db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_LINK)) return -1; 6537db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_UNLINK)) return -1; 6547db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_PLINK)) return -1; 6557db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, I_PUNLINK)) return -1; 6567db96d56Sopenharmony_ci#endif 6577db96d56Sopenharmony_ci#ifdef F_ADD_SEALS 6587db96d56Sopenharmony_ci /* Linux: file sealing for memfd_create() */ 6597db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_ADD_SEALS)) return -1; 6607db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_GET_SEALS)) return -1; 6617db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SEAL_SEAL)) return -1; 6627db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SEAL_SHRINK)) return -1; 6637db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SEAL_GROW)) return -1; 6647db96d56Sopenharmony_ci if (PyModule_AddIntMacro(m, F_SEAL_WRITE)) return -1; 6657db96d56Sopenharmony_ci#endif 6667db96d56Sopenharmony_ci return 0; 6677db96d56Sopenharmony_ci} 6687db96d56Sopenharmony_ci 6697db96d56Sopenharmony_cistatic int 6707db96d56Sopenharmony_cifcntl_exec(PyObject *module) 6717db96d56Sopenharmony_ci{ 6727db96d56Sopenharmony_ci if (all_ins(module) < 0) { 6737db96d56Sopenharmony_ci return -1; 6747db96d56Sopenharmony_ci } 6757db96d56Sopenharmony_ci return 0; 6767db96d56Sopenharmony_ci} 6777db96d56Sopenharmony_ci 6787db96d56Sopenharmony_cistatic PyModuleDef_Slot fcntl_slots[] = { 6797db96d56Sopenharmony_ci {Py_mod_exec, fcntl_exec}, 6807db96d56Sopenharmony_ci {0, NULL} 6817db96d56Sopenharmony_ci}; 6827db96d56Sopenharmony_ci 6837db96d56Sopenharmony_cistatic struct PyModuleDef fcntlmodule = { 6847db96d56Sopenharmony_ci PyModuleDef_HEAD_INIT, 6857db96d56Sopenharmony_ci .m_name = "fcntl", 6867db96d56Sopenharmony_ci .m_doc = module_doc, 6877db96d56Sopenharmony_ci .m_size = 0, 6887db96d56Sopenharmony_ci .m_methods = fcntl_methods, 6897db96d56Sopenharmony_ci .m_slots = fcntl_slots, 6907db96d56Sopenharmony_ci}; 6917db96d56Sopenharmony_ci 6927db96d56Sopenharmony_ciPyMODINIT_FUNC 6937db96d56Sopenharmony_ciPyInit_fcntl(void) 6947db96d56Sopenharmony_ci{ 6957db96d56Sopenharmony_ci return PyModuleDef_Init(&fcntlmodule); 6967db96d56Sopenharmony_ci} 697