http://gcc.gnu.org/wiki/Visibility
http://gcc.gnu.org/onlinedocs/gcc-3.3.6/gcc/Function-Attributes.html#Function-Attributes
This can be done by adding C<-fvisibility=hidden> to CFLAGS and setting
PARROT_API to C<__attribute__ ((visibility("default")))>.
If you're trying this, prepare to kill io_4 quickly while t/src/io.t is
running, as it would print "16777215:" for a very, very long time
(there's already a ticket for this). The following is r18140 on Ubuntu,
using GCC 4.1.2.
>prove t/src/io.t
...
t/src/io....ok 15/20# 'cc -L/usr/local/lib -Wl,-E t/src/io_16.o
src/parrot_config.o -o t/src/io_16 -Wl,-rpath=/home/rb
lasch/src/parrot/trunk/blib/lib -Lblib/lib -lparrot -lpthread -lm
-L/usr/lib -licuuc -licudata -lpthread -lm -ldl -lm -
lpthread -lcrypt -lrt -lgmp -lreadline -lncurses' failed with exit code 1
# Failed to build 't/src/io_16': t/src/io_16.o: In function `the_test':
# t/src/io_16.c:31: undefined reference to `PIO_make_offset'
# collect2: ld returned 1 exit status
# Failed test (t/src/io.t at line 506)
t/src/io....NOK 16# 'cc -L/usr/local/lib -Wl,-E t/src/io_17.o
src/parrot_config.o -o t/src/io_17 -Wl,-rpath=/home/rbla
sch/src/parrot/trunk/blib/lib -Lblib/lib -lparrot -lpthread -lm
-L/usr/lib -licuuc -licudata -lpthread -lm -ldl -lm -lp
thread -lcrypt -lrt -lgmp -lreadline -lncurses' failed with exit code 1
# Failed to build 't/src/io_17': t/src/io_17.o: In function `the_test':
# t/src/io_17.c:46: undefined reference to `PIO_make_offset'
# collect2: ld returned 1 exit status
# Failed test (t/src/io.t at line 538)
t/src/io....NOK 17# 'cc -L/usr/local/lib -Wl,-E t/src/io_18.o
src/parrot_config.o -o t/src/io_18 -Wl,-rpath=/home/rbla
sch/src/parrot/trunk/blib/lib -Lblib/lib -lparrot -lpthread -lm
-L/usr/lib -licuuc -licudata -lpthread -lm -ldl -lm -lp
thread -lcrypt -lrt -lgmp -lreadline -lncurses' failed with exit code 1
# Failed to build 't/src/io_18': t/src/io_18.o: In function `the_test':
# t/src/io_18.c:33: undefined reference to `PIO_STDOUT'
# collect2: ld returned 1 exit status
# Failed test (t/src/io.t at line 593)
t/src/io....NOK 18# 'cc -L/usr/local/lib -Wl,-E t/src/io_19.o
src/parrot_config.o -o t/src/io_19 -Wl,-rpath=/home/rbla
sch/src/parrot/trunk/blib/lib -Lblib/lib -lparrot -lpthread -lm
-L/usr/lib -licuuc -licudata -lpthread -lm -ldl -lm -lp
thread -lcrypt -lrt -lgmp -lreadline -lncurses' failed with exit code 1
# Failed to build 't/src/io_19': t/src/io_19.o: In function `the_test':
# t/src/io_19.c:29: undefined reference to `pio_stdio_layer'
# collect2: ld returned 1 exit status
# Failed test (t/src/io.t at line 628)
t/src/io....ok 20/20# Looks like you failed 9 tests of 20.
t/src/io....dubious
Test returned status 9 (wstat 2304, 0x900)
DIED. FAILED tests 2-4, 6-7, 16-19
Failed 9/20 tests, 55.00% okay
Failed Test Stat Wstat Total Fail Failed List of Failed
-------------------------------------------------------------------------------
t/src/io.t 9 2304 20 9 45.00% 2-4 6-7 16-19
Failed 1/1 test scripts, 0.00% okay. 9/20 subtests failed, 55.00% okay.
Ron
I think that we need to tread very carefully with adding additional
gcc-isms to Parrot, lest we break compatibility with additional compilers
even further. If Parrot will run everywhere, we need to think about
working more towards ANSI and POSIX compliance.
Steve Peters
st...@fisharerojo.org
On the other hand, we've managed very well in Perl 5 with the flag data in
embed.fnc and generating the annotated headers programmatically.
I think it would have been nice to have had something like this some years
ago (er, maybe 10) to prevent the magpies from turning any and every function
in the Perl 5 core into part of the supported API.
Particularly given that on some platforms (such as Win32) API functions need
to be exported explicitly, resulting in modules written on *nix platforms
not working on Win32.
(and actually, I'm tempted to add it even now to Perl 5 to enforce what
remains of our sanity)
Nicholas Clark
I think that the same effect can be achieved using a linker script (although
I don't know much about them), in wich case you are not depending on a
compiler feature.
I thought the same, but I've never seen clear documentation as to how to do it.
Nicholas Clark
Just to elaborate a bit further on what I did: There's a macro called
PARROT_API (see F<include/parrot/config.h>) which is used to tag all
symbols to be exported. On Win32 it expands to C<__declspec(dllexport)>
to export the symbol (see F<config/init/hints/mswin32.pm>), for others
to nothing. For my test I defined it as C<__attribute__ ((visibility
("default")))>.
Ron
> My view of this is something along these lines. You can use any
> function you want at all, but if it's not documented as part of the
> supported API, there's nothing saying I won't purposely break your code
> in the next release. In big bold red letters of course.
>
> >Particularly given that on some platforms (such as Win32) API
> >functions need
> >to be exported explicitly, resulting in modules written on *nix
> >platforms
> >not working on Win32.
The problem is that between now and that next release, someone inevitably
writes something on Linux that doesn't work on Win32, and they blame everyone
but themselves.
I'd much prefer to nip the problem in the bud by preventing the code from
ever being shipped.
Nicholas Clark
> On Thu, Apr 12, 2007 at 09:13:14AM -0500, Steve Peters wrote:
>> On Thu, Apr 12, 2007 at 01:37:24PM +0200, Ron Blaschke wrote:
>>
>> I think that we need to tread very carefully with adding additional
>> gcc-isms to Parrot, lest we break compatibility with additional
>> compilers
>> even further. If Parrot will run everywhere, we need to think about
>> working more towards ANSI and POSIX compliance.
>
> On the other hand, we've managed very well in Perl 5 with the flag
> data in
> embed.fnc and generating the annotated headers programmatically.
>
> I think it would have been nice to have had something like this some
> years
> ago (er, maybe 10) to prevent the magpies from turning any and every
> function
> in the Perl 5 core into part of the supported API.
>
My view of this is something along these lines. You can use any
function you want at all, but if it's not documented as part of the
supported API, there's nothing saying I won't purposely break your code
in the next release. In big bold red letters of course.
> Particularly given that on some platforms (such as Win32) API
when designing and implementing parrot's embedding/extending api, it'd
be nice if the linker failed on platforms other than windows. this
patch will accomplish that nicely.
~jerry
I think it's been a while since we had many failure free smokes. Is
there/does someone know of a better "smoking" module to make it easily
to test failures and if it's architecture specific, or operating system
specific, or both. There's a few problems with freebsd on amd64 which
may largely be configuration(freebsd is amd64, not x86_64).
Portability on parrot is more than a problem of exported symbols at the
moment. I think we've become overly accustomed to having test
failures, but some installer scripts won't install if there's a single
failure, which may be something trivial.
> On the other hand, we've managed very well in Perl 5 with the flag data in
> embed.fnc and generating the annotated headers programmatically.
Interesting. I quite like this.
> Nicholas Clark
Ron
ld scripts have non-portability issues as well.
At my day job, we make heavy use of gcc attributes protected in #ifdef
blocks. E.g.
...
#ifdef __GNUC__
) __attribute__((format(printf, 6, 7)));
#else // __GNUC__
);
#endif // __GNUC__
While this certainly does clutter up the headers we've decided that the
additional features, optimization, & error checking allowed by the use of
attributes are worth it. Machine generating the headers would be better
but we don't have to support non-POSIX like platforms so it hasn't been
worth the effort.
My guess is that the majority of Parrot users are building it with gcc
and just the extra error checking possible from using a rich set of
attributes would benefit all platforms (compile time NULL checking,
etc.). In fact, I'd vote for using the literal gcc attribute syntax
without protective #ifdefs and then mangling and/or removing
unsupported constructs for the target platform.
-J
--