@@ -3078,18 +3078,22 @@ class Py_off_t_return_converter(long_return_converter):
30783078 type = 'Py_off_t'
30793079 conversion_fn = 'PyLong_FromPy_off_t'
30803080
3081- class path_confname_converter (CConverter):
3081+ class confname_converter (CConverter):
30823082 type="int"
3083- converter="conv_path_confname "
3083+ converter="conv_confname "
30843084
3085- class confstr_confname_converter(path_confname_converter ):
3086- converter='conv_confstr_confname'
3085+ def converter_init(self, *, table ):
3086+ self.table = table
30873087
3088- class sysconf_confname_converter(path_confname_converter):
3089- converter="conv_sysconf_confname"
3088+ def parse_arg(self, argname, displayname, *, limited_capi):
3089+ return self.format_code("""
3090+ if (!{converter}(module, {argname}, &{paramname}, "{table}")) {{{{
3091+ goto exit;
3092+ }}}}
3093+ """, argname=argname, converter=self.converter, table=self.table)
30903094
30913095[python start generated code]*/
3092- /*[python end generated code: output=da39a3ee5e6b4b0d input=577cb476e5d64960 ]*/
3096+ /*[python end generated code: output=da39a3ee5e6b4b0d input=a6199b1618d73f53 ]*/
30933097
30943098/*[clinic input]
30953099
@@ -13503,46 +13507,38 @@ struct constdef {
1350313507};
1350413508
1350513509static int
13506- conv_confname (PyObject * arg , int * valuep , struct constdef * table ,
13507- size_t tablesize )
13510+ conv_confname (PyObject * module , PyObject * arg , int * valuep , const char * tablename )
1350813511{
13509- if (PyLong_Check (arg )) {
13510- int value = PyLong_AsInt (arg );
13511- if (value == -1 && PyErr_Occurred ())
13512- return 0 ;
13513- * valuep = value ;
13514- return 1 ;
13515- }
13516- else {
13517- /* look up the value in the table using a binary search */
13518- size_t lo = 0 ;
13519- size_t mid ;
13520- size_t hi = tablesize ;
13521- int cmp ;
13522- const char * confname ;
13523- if (!PyUnicode_Check (arg )) {
13524- PyErr_SetString (PyExc_TypeError ,
13525- "configuration names must be strings or integers" );
13512+ if (PyUnicode_Check (arg )) {
13513+ PyObject * table = PyObject_GetAttrString (module , tablename );
13514+ if (table == NULL ) {
1352613515 return 0 ;
1352713516 }
13528- confname = PyUnicode_AsUTF8 (arg );
13529- if (confname == NULL )
13517+
13518+ arg = PyObject_GetItem (table , arg );
13519+ Py_DECREF (table );
13520+ if (arg == NULL ) {
13521+ PyErr_SetString (
13522+ PyExc_ValueError , "unrecognized configuration name" );
1353013523 return 0 ;
13531- while (lo < hi ) {
13532- mid = (lo + hi ) / 2 ;
13533- cmp = strcmp (confname , table [mid ].name );
13534- if (cmp < 0 )
13535- hi = mid ;
13536- else if (cmp > 0 )
13537- lo = mid + 1 ;
13538- else {
13539- * valuep = table [mid ].value ;
13540- return 1 ;
13541- }
1354213524 }
13543- PyErr_SetString (PyExc_ValueError , "unrecognized configuration name" );
13544- return 0 ;
13525+ } else {
13526+ Py_INCREF (arg ); // Match the Py_DECREF below.
13527+ }
13528+
13529+ int success = 0 ;
13530+ if (!PyLong_Check (arg )) {
13531+ PyErr_SetString (PyExc_TypeError ,
13532+ "configuration names must be strings or integers" );
13533+ } else {
13534+ int value = PyLong_AsInt (arg );
13535+ if (!(value == -1 && PyErr_Occurred ())) {
13536+ * valuep = value ;
13537+ success = 1 ;
13538+ }
1354513539 }
13540+ Py_DECREF (arg );
13541+ return success ;
1354613542}
1354713543
1354813544
@@ -13633,14 +13629,6 @@ static struct constdef posix_constants_pathconf[] = {
1363313629 {"PC_TIMESTAMP_RESOLUTION" , _PC_TIMESTAMP_RESOLUTION },
1363413630#endif
1363513631};
13636-
13637- static int
13638- conv_path_confname (PyObject * arg , int * valuep )
13639- {
13640- return conv_confname (arg , valuep , posix_constants_pathconf ,
13641- sizeof (posix_constants_pathconf )
13642- / sizeof (struct constdef ));
13643- }
1364413632#endif
1364513633
1364613634
@@ -13649,7 +13637,7 @@ conv_path_confname(PyObject *arg, int *valuep)
1364913637os.fpathconf -> long
1365013638
1365113639 fd: fildes
13652- name: path_confname
13640+ name: confname(table="pathconf_names")
1365313641 /
1365413642
1365513643Return the configuration limit name for the file descriptor fd.
@@ -13659,7 +13647,7 @@ If there is no limit, return -1.
1365913647
1366013648static long
1366113649os_fpathconf_impl (PyObject * module , int fd , int name )
13662- /*[clinic end generated code: output=d5b7042425fc3e21 input=5b8d2471cfaae186 ]*/
13650+ /*[clinic end generated code: output=d5b7042425fc3e21 input=023d44589c9ed6aa ]*/
1366313651{
1366413652 long limit ;
1366513653
@@ -13677,7 +13665,7 @@ os_fpathconf_impl(PyObject *module, int fd, int name)
1367713665/*[clinic input]
1367813666os.pathconf -> long
1367913667 path: path_t(allow_fd='PATH_HAVE_FPATHCONF')
13680- name: path_confname
13668+ name: confname(table="pathconf_names")
1368113669
1368213670Return the configuration limit name for the file or directory path.
1368313671
@@ -13688,7 +13676,7 @@ On some platforms, path may also be specified as an open file descriptor.
1368813676
1368913677static long
1369013678os_pathconf_impl (PyObject * module , path_t * path , int name )
13691- /*[clinic end generated code: output=5bedee35b293a089 input=bc3e2a985af27e5e ]*/
13679+ /*[clinic end generated code: output=5bedee35b293a089 input=6f6072f57b10c787 ]*/
1369213680{
1369313681 long limit ;
1369413682
@@ -13865,27 +13853,19 @@ static struct constdef posix_constants_confstr[] = {
1386513853#endif
1386613854};
1386713855
13868- static int
13869- conv_confstr_confname (PyObject * arg , int * valuep )
13870- {
13871- return conv_confname (arg , valuep , posix_constants_confstr ,
13872- sizeof (posix_constants_confstr )
13873- / sizeof (struct constdef ));
13874- }
13875-
1387613856
1387713857/*[clinic input]
1387813858os.confstr
1387913859
13880- name: confstr_confname
13860+ name: confname(table="confstr_names")
1388113861 /
1388213862
1388313863Return a string-valued system configuration variable.
1388413864[clinic start generated code]*/
1388513865
1388613866static PyObject *
1388713867os_confstr_impl (PyObject * module , int name )
13888- /*[clinic end generated code: output=bfb0b1b1e49b9383 input=18fb4d0567242e65 ]*/
13868+ /*[clinic end generated code: output=bfb0b1b1e49b9383 input=4c6ffca2837ec959 ]*/
1388913869{
1389013870 PyObject * result = NULL ;
1389113871 char buffer [255 ];
@@ -14422,26 +14402,18 @@ static struct constdef posix_constants_sysconf[] = {
1442214402#endif
1442314403};
1442414404
14425- static int
14426- conv_sysconf_confname (PyObject * arg , int * valuep )
14427- {
14428- return conv_confname (arg , valuep , posix_constants_sysconf ,
14429- sizeof (posix_constants_sysconf )
14430- / sizeof (struct constdef ));
14431- }
14432-
1443314405
1443414406/*[clinic input]
1443514407os.sysconf -> long
14436- name: sysconf_confname
14408+ name: confname(table="sysconf_names")
1443714409 /
1443814410
1443914411Return an integer-valued system configuration variable.
1444014412[clinic start generated code]*/
1444114413
1444214414static long
1444314415os_sysconf_impl (PyObject * module , int name )
14444- /*[clinic end generated code: output=3662f945fc0cc756 input=279e3430a33f29e4 ]*/
14416+ /*[clinic end generated code: output=3662f945fc0cc756 input=930b8f23b5d15086 ]*/
1444514417{
1444614418 long value ;
1444714419
@@ -14454,40 +14426,15 @@ os_sysconf_impl(PyObject *module, int name)
1445414426#endif /* HAVE_SYSCONF */
1445514427
1445614428
14457- /* This code is used to ensure that the tables of configuration value names
14458- * are in sorted order as required by conv_confname(), and also to build
14459- * the exported dictionaries that are used to publish information about the
14460- * names available on the host platform.
14461- *
14462- * Sorting the table at runtime ensures that the table is properly ordered
14463- * when used, even for platforms we're not able to test on. It also makes
14464- * it easier to add additional entries to the tables.
14465- */
14466-
14467- static int
14468- cmp_constdefs (const void * v1 , const void * v2 )
14469- {
14470- const struct constdef * c1 =
14471- (const struct constdef * ) v1 ;
14472- const struct constdef * c2 =
14473- (const struct constdef * ) v2 ;
14474-
14475- return strcmp (c1 -> name , c2 -> name );
14476- }
14477-
1447814429static int
1447914430setup_confname_table (struct constdef * table , size_t tablesize ,
1448014431 const char * tablename , PyObject * module )
1448114432{
14482- PyObject * d = NULL ;
14483- size_t i ;
14484-
14485- qsort (table , tablesize , sizeof (struct constdef ), cmp_constdefs );
14486- d = PyDict_New ();
14433+ PyObject * d = PyDict_New ();
1448714434 if (d == NULL )
1448814435 return -1 ;
1448914436
14490- for (i = 0 ; i < tablesize ; ++ i ) {
14437+ for (size_t i = 0 ; i < tablesize ; ++ i ) {
1449114438 PyObject * o = PyLong_FromLong (table [i ].value );
1449214439 if (o == NULL || PyDict_SetItemString (d , table [i ].name , o ) == -1 ) {
1449314440 Py_XDECREF (o );
0 commit comments