Perl / perl5

🐪 The Perl programming language
https://dev.perl.org/perl5/
Other
1.93k stars 549 forks source link

h2xs: Support for _Bool/stdbool.h? #15777

Open p5pRT opened 7 years ago

p5pRT commented 7 years ago

Migrated from rt.perl.org#130393 (status was 'open')

Searchable as RT130393$

p5pRT commented 7 years ago

From tauner@technikum-wien.at

Hi\,

I have used h2xs for the first time today to start the creation of a Perl package based on a small C library. make failed to build it apparently due to the usage of a bool type for a parameter in one of the library's exported functions resulting in

error​: ‘arg1’ undeclared (first use in this function)   RETVAL = dap_poll(context\, arg1);

The generated code in the .xs is​:

XS_EUPXS(XS_function_name) {   dVAR; dXSARGS;   if (items != 2)   croak_xs_usage(cv\, "context\, arg1");   {   struct some_context * context;   int RETVAL;   dXSTARG; [...]

Note that there is no variable definition for "arg1" (whose name is actually made up by h2xs apparently - in the library it is called wait).

When I change the library to use int instead of bool (or _Bool) then the parameter is handled correctly (NB​: "wait" in the croak_xs_usage() call)​:

XS_EUPXS(XS_function_name) {   dVAR; dXSARGS;   if (items != 2)   croak_xs_usage(cv\, "context\, wait");   {   struct some_context * context;   int wait = (int)SvIV(ST(1)) ;   int RETVAL;   dXSTARG; [...]

_Bool is a C type introduced in C99\, bool is a typedef declared by stdbool.h also from C99 and nothing fancy at all. I am using h2xs from ubuntu's Perl 5.22.1 but I could not find any hint on bool support in h2xs in Perl git thus I am reporting this here.

KR -- Dipl.-Ing. Stefan Tauner Research and Development Embedded Systems Department

University of Applied Sciences Technikum Wien Hoechstaedtplatz 6\, 1200 Vienna\, Austria T​: +43 1 333 40 77-316 E​: stefan.tauner@​technikum-wien.at I​: embsys.technikum-wien.at I​: www.technikum-wien.at

p5pRT commented 7 years ago

From @iabyn

On Fri\, Dec 23\, 2016 at 07​:10​:27AM -0800\, Stefan Tauner wrote​:

I have used h2xs for the first time today to start the creation of a Perl package based on a small C library. make failed to build it apparently due to the usage of a bool type for a parameter in one of the library's exported functions resulting in

error​: ‘arg1’ undeclared (first use in this function)

Can you show us​:

1) the command-line your are invoking h2xs with; 2) the relevant declarations(s) from the .h file (or even better\, attach a short stripped down and self-contained .h file that reproduces the problem); 2) attach the output of 'perl -V' for the perl used to execute h2xs.

Thanks.

-- The Enterprise's efficient long-range scanners detect a temporal vortex distortion in good time\, allowing it to be safely avoided via a minor course correction.   -- Things That Never Happen in "Star Trek" #21

p5pRT commented 7 years ago

The RT System itself - Status changed from 'new' to 'open'

p5pRT commented 7 years ago

From tauner@technikum-wien.at

On Sun\, 25 Dec 2016 11​:21​:10 -0800 "Dave Mitchell via RT" \perlbug\-followup@​perl\.org wrote​:

On Fri\, Dec 23\, 2016 at 07​:10​:27AM -0800\, Stefan Tauner wrote​:

I have used h2xs for the first time today to start the creation of a Perl package based on a small C library. make failed to build it apparently due to the usage of a bool type for a parameter in one of the library's exported functions resulting in

error​: ‘arg1’ undeclared (first use in this function)

Can you show us​:

1) the command-line your are invoking h2xs with;

h2xs -x booltest.h So this might be a bug in C​::Scan (which I have installed via cpanm from HVDS/C-Scan-0.74)?

2) the relevant declarations(s) from the .h file (or even better\, attach a short stripped down and self-contained .h file that reproduces the problem);

booltest.h​:

  #include \<stdbool.h>   void h2xs(bool b);

With a trivial implementation in booltest.c​:

  #include "booltest.h"   void h2xs(bool b) {   (void)b;   }

However\, the same thing works fine with _Bool instead of bool+stdbool.h.

2) attach the output of 'perl -V' for the perl used to execute h2xs.

See attached perl.V

KR -- Dipl.-Ing. Stefan Tauner Research and Development Embedded Systems Department

University of Applied Sciences Technikum Wien Hoechstaedtplatz 6\, 1200 Vienna\, Austria T​: +43 1 333 40 77-316 E​: stefan.tauner@​technikum-wien.at I​: embsys.technikum-wien.at I​: www.technikum-wien.at

p5pRT commented 7 years ago

From tauner@technikum-wien.at

perl.V

p5pRT commented 7 years ago

From @jkeenan

On Wed\, 28 Dec 2016 06​:00​:21 GMT\, tauner@​technikum-wien.at wrote​:

h2xs -x booltest.h So this might be a bug in C​::Scan (which I have installed via cpanm from HVDS/C-Scan-0.74)?

What happens if you do not use the '-x' option and thereby avoid C​::Scan?

(When I did that\, 'make' completed -- but since I've rarely attempted to write XS I don't know whether that's meaningful or not.)

Thank you very much.

-- James E Keenan (jkeenan@​cpan.org)

p5pRT commented 7 years ago

From @iabyn

On Wed\, Dec 28\, 2016 at 05​:37​:04AM -0800\, James E Keenan via RT wrote​:

On Wed\, 28 Dec 2016 06​:00​:21 GMT\, tauner@​technikum-wien.at wrote​:

h2xs -x booltest.h So this might be a bug in C​::Scan (which I have installed via cpanm from HVDS/C-Scan-0.74)?

What happens if you do not use the '-x' option and thereby avoid C​::Scan?

(When I did that\, 'make' completed -- but since I've rarely attempted to write XS I don't know whether that's meaningful or not.)

Thank you very much.

When foo\,h contains this​:

  #include \<stdbool.h>   void h2xs(bool b);

then h2xs -x foo.h\, via C​::Scan\, is generating an XS file that looks like​:

  void   h2xs(arg0)

which is being converted into the C code

  XS_EUPXS(XS_Foo_h2xs); /* prototype to pass -Wmissing-prototypes */   XS_EUPXS(XS_Foo_h2xs)   {   dVAR; dXSARGS;   if (items != 1)   croak_xs_usage(cv\, "arg0");   {

  h2xs(arg0);   }   XSRETURN_EMPTY;   }

The issues seem to be that

1) h2xs and/or C​::Scan isn't including the variable type for arg0 in the generated XS; I assume that it should have output​:

  void   h2xs(bool arg0)

2) that ExtUtils/xsubpp isn't seeing that as an error and is instead converting it onto invalid C code\, by not including the line​:

  bool arg0 = (bool)SvTRUE(ST(0))

Does anyone here more familiar with XS want to comment?

-- Indomitable in retreat\, invincible in advance\, insufferable in victory   -- Churchill on Montgomery

p5pRT commented 7 years ago

From tauner@technikum-wien.at

On Wed\, 28 Dec 2016 05​:37​:04 -0800 "James E Keenan via RT" \perlbug\-followup@&#8203;perl\.org wrote​:

On Wed\, 28 Dec 2016 06​:00​:21 GMT\, tauner@​technikum-wien.at wrote​:

h2xs -x booltest.h So this might be a bug in C​::Scan (which I have installed via cpanm from HVDS/C-Scan-0.74)?

What happens if you do not use the '-x' option and thereby avoid C​::Scan?

(When I did that\, 'make' completed -- but since I've rarely attempted to write XS I don't know whether that's meaningful or not.)

Yes\, then it succeeds because the functions are not wrapped at all :) I don't know if that's on purpose or a bug\, but I presume the former. I have no idea how it can be used without that though. Maybe to just prepare a skeleton package...

KR -- Dipl.-Ing. Stefan Tauner Research and Development Embedded Systems Department

University of Applied Sciences Technikum Wien Hoechstaedtplatz 6\, 1200 Vienna\, Austria T​: +43 1 333 40 77-316 E​: stefan.tauner@​technikum-wien.at I​: embsys.technikum-wien.at I​: www.technikum-wien.at

p5pRT commented 7 years ago

From @Leont

On Fri\, Dec 23\, 2016 at 4​:10 PM\, Stefan Tauner \perlbug\-followup@&#8203;perl\.org wrote

_Bool is a C type introduced in C99\, bool is a typedef declared by stdbool.h also from C99 and nothing fancy at all. I am using h2xs from ubuntu's Perl 5.22.1 but I could not find any hint on bool support in h2xs in Perl git thus I am reporting this here.

_Bool is indeed a C99 built-in type\, but bool is a *macro* to _Bool\, not a typedef. This apparently confuses h2xs/C​::Scan\, which I don't think is entirely unreasonable given the alternative.

I would recommend using _Bool instead of bool\, that seems to generate sensible XS if you add a one line typemap file to your distribution containing _Bool T_BOOL

Leon

p5pRT commented 7 years ago

From @hvds

On Wed\, 28 Dec 2016 07​:13​:36 -0800\, davem wrote​:

On Wed\, Dec 28\, 2016 at 05​:37​:04AM -0800\, James E Keenan via RT wrote​:

On Wed\, 28 Dec 2016 06​:00​:21 GMT\, tauner@​technikum-wien.at wrote​:

h2xs -x booltest.h So this might be a bug in C​::Scan (which I have installed via cpanm from HVDS/C-Scan-0.74)?

What happens if you do not use the '-x' option and thereby avoid C​::Scan?

(When I did that\, 'make' completed -- but since I've rarely attempted to write XS I don't know whether that's meaningful or not.)

Thank you very much.

When foo\,h contains this​:

#include \<stdbool.h> void h2xs(bool b);

then h2xs -x foo.h\, via C​::Scan\, is generating an XS file that looks like​:

void h2xs(arg0)

I'll try to take a look later this week at the C​::Scan side\, to see if this is fixable; I don't have stdbool.h here\, but I'm guessing that something like \<http​://clang.llvm.org/doxygen/stdbool_8h_source.html> should be close enough.

Hugo

p5pRT commented 7 years ago

From @iabyn

On Wed\, Dec 28\, 2016 at 11​:56​:11PM -0800\, Hugo van der Sanden via RT wrote​:

On Wed\, 28 Dec 2016 07​:13​:36 -0800\, davem wrote​:

On Wed\, Dec 28\, 2016 at 05​:37​:04AM -0800\, James E Keenan via RT wrote​:

On Wed\, 28 Dec 2016 06​:00​:21 GMT\, tauner@​technikum-wien.at wrote​:

h2xs -x booltest.h So this might be a bug in C​::Scan (which I have installed via cpanm from HVDS/C-Scan-0.74)?

What happens if you do not use the '-x' option and thereby avoid C​::Scan?

(When I did that\, 'make' completed -- but since I've rarely attempted to write XS I don't know whether that's meaningful or not.)

Thank you very much.

When foo\,h contains this​:

#include \<stdbool.h> void h2xs(bool b);

then h2xs -x foo.h\, via C​::Scan\, is generating an XS file that looks like​:

void h2xs(arg0)

I'll try to take a look later this week at the C​::Scan side\, to see if this is fixable; I don't have stdbool.h here\, but I'm guessing that something like \<http​://clang.llvm.org/doxygen/stdbool_8h_source.html> should be close enough.

It seems very sensitive. I tried as small a change as replacing this line​:

  #include \<stdbool.h>

with this this line

  #include "/usr/lib/gcc/x86_64-redhat-linux/5.3.1/include/stdbool.h"

(which from stracing the h2xs command appears to be the file it reads) and the problem magically goes away.

That file is attached.

-- Lear​: Dost thou call me fool\, boy? Fool​: All thy other titles thou hast given away; that thou wast born with.

p5pRT commented 7 years ago

From @iabyn

/* Copyright (C) 1998-2015 Free Software Foundation\, Inc.

This file is part of GCC.

GCC is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3\, or (at your option) any later version.

GCC is distributed in the hope that it will be useful\, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

Under Section 7 of GPL version 3\, you are granted additional permissions described in the GCC Runtime Library Exception\, version 3.1\, as published by the Free Software Foundation.

You should have received a copy of the GNU General Public License and a copy of the GCC Runtime Library Exception along with this program; see the files COPYING3 and COPYING.RUNTIME respectively. If not\, see \<http​://www.gnu.org/licenses/>. */

/* * ISO C Standard​: 7.16 Boolean type and values \<stdbool.h> */

#ifndef _STDBOOL_H #define _STDBOOL_H

#ifndef __cplusplus

#define bool _Bool #define true 1 #define false 0

#else /* __cplusplus */

/* Supporting _Bool in C++ is a GCC extension. */ #define _Bool bool

#if __cplusplus \< 201103L /* Defining these macros in C++98 is a GCC extension. */ #define bool bool #define false false #define true true #endif

#endif /* __cplusplus */

/* Signal that all the definitions are present. */ #define __bool_true_false_are_defined 1

#endif /* stdbool.h */

p5pRT commented 7 years ago

From @hvds

On Wed\, 28 Dec 2016 07​:13​:36 -0800\, davem wrote​:

When foo\,h contains this​:

#include \<stdbool.h> void h2xs(bool b);

then h2xs -x foo.h\, via C​::Scan\, is generating an XS file that looks like​:

void h2xs(arg0)

which is being converted into the C code

XS_EUPXS(XS_Foo_h2xs); /* prototype to pass -Wmissing-prototypes */ XS_EUPXS(XS_Foo_h2xs) { dVAR; dXSARGS; if (items != 1) croak_xs_usage(cv\, "arg0"); {

h2xs(arg0); } XSRETURN_EMPTY; }

The issues seem to be that

1) h2xs and/or C​::Scan isn't including the variable type for arg0 in the generated XS; I assume that it should have output​:

void h2xs(bool arg0)

I'm seeing it output this (which I believe is correct)​: void h2xs(b)   _Bool b

2) that ExtUtils/xsubpp isn't seeing that as an error and is instead converting it onto invalid C code\, by not including the line​:

bool arg0 = (bool)SvTRUE(ST(0))

For me\, xsubpp is giving this​:

  _Bool b;

  if (SvROK(ST(0)) && sv_derived_from(ST(0)\, "_Bool")) {   IV tmp = SvIV((SV*)SvRV(ST(0)));   b = INT2PTR(_Bool\,tmp);   }   else [...]

I haven't been able to reproduce the case of a missing '_Bool b' declaration in Foo.xs\, so I'm stuck on this for now.

Hugo

p5pRT commented 7 years ago

From @Leont

On Sat\, Dec 31\, 2016 at 3​:04 PM\, Hugo van der Sanden via RT \< perlbug-followup@​perl.org> wrote​:

On Wed\, 28 Dec 2016 07​:13​:36 -0800\, davem wrote​:

When foo\,h contains this​:

#include \<stdbool.h> void h2xs(bool b);

then h2xs -x foo.h\, via C​::Scan\, is generating an XS file that looks like​:

void h2xs(arg0)

which is being converted into the C code

XS_EUPXS(XS_Foo_h2xs); /* prototype to pass -Wmissing-prototypes */ XS_EUPXS(XS_Foo_h2xs) { dVAR; dXSARGS; if (items != 1) croak_xs_usage(cv\, "arg0"); {

h2xs(arg0); } XSRETURN_EMPTY; }

The issues seem to be that

1) h2xs and/or C​::Scan isn't including the variable type for arg0 in the generated XS; I assume that it should have output​:

void h2xs(bool arg0)

I'm seeing it output this (which I believe is correct)​: void h2xs(b) _Bool b

2) that ExtUtils/xsubpp isn't seeing that as an error and is instead converting it onto invalid C code\, by not including the line​:

bool arg0 = (bool)SvTRUE(ST(0))

For me\, xsubpp is giving this​:

\_Bool   b;

if \(SvROK\(ST\(0\)\) && sv\_derived\_from\(ST\(0\)\, "\_Bool"\)\) \{
    IV tmp = SvIV\(\(SV\*\)SvRV\(ST\(0\)\)\);
    b = INT2PTR\(\_Bool\,tmp\);
\}
else \[\.\.\.\]

I haven't been able to reproduce the case of a missing '_Bool b' declaration in Foo.xs\, so I'm stuck on this for now.

Hugo

It seems to assume _Bool is some kind of object type\, for some reason\, hence my previous suggestion for an explicit typemap.

Leon