125
125
# define HAVE_PWRITEV_RUNTIME __builtin_available(macOS 11.0, iOS 14.0, tvOS 14.0, watchOS 7.0, *)
126
126
# define HAVE_MKFIFOAT_RUNTIME __builtin_available(macOS 13.0, iOS 16.0, tvOS 16.0, watchOS 9.0, *)
127
127
# define HAVE_MKNODAT_RUNTIME __builtin_available(macOS 13.0, iOS 16.0, tvOS 16.0, watchOS 9.0, *)
128
+ # define HAVE_PTSNAME_R_RUNTIME __builtin_available(macOS 10.13.4, iOS 11.3, tvOS 11.3, watchOS 4.3, *)
128
129
129
130
# define HAVE_POSIX_SPAWN_SETSID_RUNTIME __builtin_available(macOS 10.15, *)
130
131
206
207
# define HAVE_MKNODAT_RUNTIME (mknodat != NULL)
207
208
# endif
208
209
210
+ # ifdef HAVE_PTSNAME_R
211
+ # define HAVE_PTSNAME_R_RUNTIME (ptsname_r != NULL)
212
+ # endif
213
+
209
214
#endif
210
215
211
216
#ifdef HAVE_FUTIMESAT
231
236
# define HAVE_PWRITEV_RUNTIME 1
232
237
# define HAVE_MKFIFOAT_RUNTIME 1
233
238
# define HAVE_MKNODAT_RUNTIME 1
239
+ # define HAVE_PTSNAME_R_RUNTIME 1
234
240
#endif
235
241
236
242
@@ -8635,6 +8641,19 @@ os_unlockpt_impl(PyObject *module, int fd)
8635
8641
#endif /* HAVE_UNLOCKPT */
8636
8642
8637
8643
#if defined(HAVE_PTSNAME ) || defined(HAVE_PTSNAME_R )
8644
+ static PyObject *
8645
+ py_ptsname (int fd )
8646
+ {
8647
+ // POSIX manpage: Upon failure, ptsname() shall return a null pointer
8648
+ // and may set errno. Always initialize errno to avoid undefined behavior.
8649
+ errno = 0 ;
8650
+ char * name = ptsname (fd );
8651
+ if (name == NULL ) {
8652
+ return posix_error ();
8653
+ }
8654
+ return PyUnicode_DecodeFSDefault (name );
8655
+ }
8656
+
8638
8657
/*[clinic input]
8639
8658
os.ptsname
8640
8659
@@ -8656,22 +8675,22 @@ os_ptsname_impl(PyObject *module, int fd)
8656
8675
int ret ;
8657
8676
char name [MAXPATHLEN + 1 ];
8658
8677
8659
- ret = ptsname_r (fd , name , sizeof (name ));
8678
+ if (HAVE_PTSNAME_R_RUNTIME ) {
8679
+ ret = ptsname_r (fd , name , sizeof (name ));
8680
+ }
8681
+ else {
8682
+ // fallback to ptsname() if ptsname_r() is not available in runtime.
8683
+ return py_ptsname (fd );
8684
+ }
8660
8685
if (ret != 0 ) {
8661
8686
errno = ret ;
8662
8687
return posix_error ();
8663
8688
}
8664
- #else
8665
- char * name ;
8666
-
8667
- name = ptsname (fd );
8668
- /* POSIX manpage: Upon failure, ptsname() shall return a null pointer and may set errno.
8669
- *MAY* set errno? Hmm... */
8670
- if (name == NULL )
8671
- return posix_error ();
8672
- #endif /* HAVE_PTSNAME_R */
8673
8689
8674
8690
return PyUnicode_DecodeFSDefault (name );
8691
+ #else
8692
+ return py_ptsname (fd );
8693
+ #endif /* HAVE_PTSNAME_R */
8675
8694
}
8676
8695
#endif /* defined(HAVE_PTSNAME) || defined(HAVE_PTSNAME_R) */
8677
8696
@@ -17739,6 +17758,9 @@ PROBE(probe_futimens, HAVE_FUTIMENS_RUNTIME)
17739
17758
PROBE (probe_utimensat , HAVE_UTIMENSAT_RUNTIME )
17740
17759
#endif
17741
17760
17761
+ #ifdef HAVE_PTSNAME_R
17762
+ PROBE (probe_ptsname_r , HAVE_PTSNAME_R_RUNTIME )
17763
+ #endif
17742
17764
17743
17765
17744
17766
@@ -17879,6 +17901,10 @@ static const struct have_function {
17879
17901
{ "HAVE_UTIMENSAT" , probe_utimensat },
17880
17902
#endif
17881
17903
17904
+ #ifdef HAVE_PTSNAME_R
17905
+ { "HAVE_PTSNAME_R" , probe_ptsname_r },
17906
+ #endif
17907
+
17882
17908
#ifdef MS_WINDOWS
17883
17909
{ "MS_WINDOWS" , NULL },
17884
17910
#endif
0 commit comments