Wiki improvements
Re: Wiki improvements
Thank you SARG, but I still do not understand. With the alias names of the procedures, everything is clear to me, I myself have used this method more than once. But with alternative names types , I don't see any practical use. Can someone give an example?
Re: Wiki improvements
Example
rand.cpp
use the command line
g++ -O2 rand.cpp -shared -o rand.dll -Wl,--kill-at,--output-def,rand.def,--out-implib,randstatic.a
Check the rand.def file to see the mangled names.
FreeBASIC test code
rand.cpp
Code: Select all
// rand.cpp
unsigned long long a,b,c,d,e;
const unsigned long long max=18446744073709551615ull;
unsigned long long& rndu()
{
e = a - ((b << 7) or (b >> (57)));
a = b xor ((c << 13) or (c >> (51)));
b = c + ((d << 37) or (d >> (27)));
c = d + e;
d = e + a;
return d;
}
void reseed(int n)
{a=n;b=n;c=n;d=n;
for(int m =n; m< n+10;m++) rndu()*=m;}
struct seed {seed() { reseed(1000000); }}; // auto seed to start
namespace {seed start;}
long long range(long long f ,long long l)
{return (rndu() % ((l-f)+1)) + f;}
double range(double f ,double l)
{return ((double)rndu()/max) * (l - f) + f;}
//g++ -O2 rand.cpp -shared -o rand.dll -Wl,--kill-at,--output-def,rand.def,--out-implib,randstatic.a
g++ -O2 rand.cpp -shared -o rand.dll -Wl,--kill-at,--output-def,rand.def,--out-implib,randstatic.a
Check the rand.def file to see the mangled names.
FreeBASIC test code
Code: Select all
#inclib "rand"
extern "C++"
declare sub reseed alias "reseed"(as long)
declare function range overload alias "range"(as longint,as longint) as longint
declare function range overload alias "range"(as double,as double) as double
end extern
reseed(10000)
for n as long=1 to 5
print range(56,78),range(4.5,5.4)
next
print
reseed(10000)
for n as long=1 to 5
print range(56,78),range(4.5,5.4)
next
print
for n as long=1 to 15
print range(56,78),range(4.5,5.4)
next
sleep
Re: Wiki improvements
dodicat!
Thanks for the example, but that's not what I asked for. I asked about:
Thanks for the example, but that's not what I asked for. I asked about:
and practical application of it. Example of how it can be used. Since this seems useless for FB and is only used to communicate with other languages, I asked for an example of how to do this.Type A Alias "AliasNameType"
i as Long
'.....
End Type
Re: Wiki improvements
@VANYA,
With this code :
How is mangled myfunc in FB for C++:
With this code :
Code: Select all
extern "C++"
type test2 as ulong 'alias "long" ''<------ line changed for different cases, see below
sub myfunc(test as test2)
test=12
end sub
end extern
Code: Select all
type test2 as long --> _Z6myfunci:
type test2 as ulong --> _Z6myfuncj:
type test2 as long alias "long" --> _Z6myfuncl:
type test2 as ulong alias "long" --> _Z6myfuncm:
Re: Wiki improvements
SARG!
I understand that internally the characters are mangled differently depending on the ALIAS!
What is the benefit to the FB programmer of this feature? Where is the practical value? How does this help in C, C++, PaSCAL, etc. code? And the main question: if this is of no use, then why was it introduced into the options TYPE????
For example, when ALIAS is used with SUB or Function - there is a benefit, because in C++ it is more convenient to declare functions in the way they are intended:
without ALIAS in FB ---- always in C++ uppercase GETTITLE
with ALIAS "GetTitle" in FB ---- declared in C++ GetTitle
Or the dodicat example confirms the usefulness ALIAS for SUB or FUNCTION.
The FBC compiler internally does a lot of things in order to generate correct code, but these subtleties, if described in the help, are useless for the average FB user. Am I wrong?
I understand that internally the characters are mangled differently depending on the ALIAS!
What is the benefit to the FB programmer of this feature? Where is the practical value? How does this help in C, C++, PaSCAL, etc. code? And the main question: if this is of no use, then why was it introduced into the options TYPE????
For example, when ALIAS is used with SUB or Function - there is a benefit, because in C++ it is more convenient to declare functions in the way they are intended:
without ALIAS in FB ---- always in C++ uppercase GETTITLE
with ALIAS "GetTitle" in FB ---- declared in C++ GetTitle
Or the dodicat example confirms the usefulness ALIAS for SUB or FUNCTION.
The FBC compiler internally does a lot of things in order to generate correct code, but these subtleties, if described in the help, are useless for the average FB user. Am I wrong?
Re: Wiki improvements
VANYA,
If someone codes many functions in FB used later with a C++ code
He/she writes only one time
and can use test2 in all those functions without writing each time test2 as ulong alias "long".
However, I agree that coding in FB for use in C++ should be very rare and only for a few users.
Maybe there are other cases but I can't imagine them.
If someone codes many functions in FB used later with a C++ code
He/she writes only one time
Code: Select all
type test2 as ulong 'alias "long"
However, I agree that coding in FB for use in C++ should be very rare and only for a few users.
Maybe there are other cases but I can't imagine them.
Re: Wiki improvements
Any C++ user can readily use fb graphics passed over as a dll.
Although, I must admit, in C++ forums, anything BASIC in origin tends to be just laughed at.
C++ people are such snobs, but you must truly admit that if you are a proficient C and C++ coder, you need not look any further to get a job done.
Although, I must admit, in C++ forums, anything BASIC in origin tends to be just laughed at.
C++ people are such snobs, but you must truly admit that if you are a proficient C and C++ coder, you need not look any further to get a job done.
Re: Wiki improvements
For those who, like me, will look for the reasons for the appearance of the ALIAS in the TYPE option:
This is only required on Windows. For example, when linking two modules written in C++ and Freebasic, the linker will give an error. Example:
FB module:
compile: fbc -nodeflibs -c FBFILE.bas
c++ module:
complile:
g++ 1.cpp -c
g++ -o test FBFILE.o 1.o
The linking error will be due to the test2 variable. However, if you write in the FB code like this:
then there will be no errors.
This is only required on Windows. For example, when linking two modules written in C++ and Freebasic, the linker will give an error. Example:
FB module:
Code: Select all
extern "C++"
type test as Long alias "long"
type test2 as Long
function func alias "func" (q1 as test , q2 as test2) as long
return q1+q2
End function
End Extern
c++ module:
Code: Select all
#include <iostream>
using namespace std;
int func(int q1 , int q2);
int main()
{
cout << func(10,20);
return 0;
}
g++ 1.cpp -c
g++ -o test FBFILE.o 1.o
The linking error will be due to the test2 variable. However, if you write in the FB code like this:
Code: Select all
...
type test as Long alias "long"
type test2 as Long alias "long"
...
Re: Wiki improvements
It might be helpful to look at 'TYPE ... AS ...' and ' ... AS <datatype> ALIAS "..."' as two separate things. They can be combined, but they need not be combined. The example you gave in your last post is incorrect.
If working in fb only:
TYPE keyword - Declare structures
TYPE (Alias) - Alternate name for any datatype within fbc only (does not affect linking)
fb on it's own should be self consistent. No need to worry about alias' and mangling.
But If also working with other languages (e.g. gcc/g++) then maybe need to know:
ALIAS - Alternate names for public symbols affecting linking, often with other programming languages
ALIAS (modifier) - Alternate names for data types only most notably with g++
I'll make some examples of each.
TYPE keyword - Declare structures
Code: Select all
type T
count as integer
sum as double
end type
dim x as T
TYPE (Alias) - Alternate name for any datatype within fbc only
also might be known as a 'typedef' in other languages
Code: Select all
type INT32 as integer<32>
type PINT32 as INT32 ptr
dim x as INT32
dim y as PINT32 = @x
ALIAS - Alternate names for public symbols affecting linking, often with other programming languages
Code: Select all
extern "c++"
sub proc alias "SomeProc"()
end sub
end extern
'' mangled name => c++ name
'' __Z8SomeProcv => SomeProc()
extern "c++"
namespace N alias "SomeNamespace"
sub S()
end sub
end namespace
end extern
'' mangled name => c++ name
'' __ZN13SomeNamespace1SEv => SomeNamespace::S()
extern "c++"
type T1
__ as integer
end type
type T2 alias "SomeOtherName"
__ as integer
end type
sub proc_t1( byref arg as T1 )
end sub
sub proc_t2( byref arg as T2 )
end sub
end extern
'' mangled name => c++ name
'' __Z7proc_t1R2T1 => proc_t1(T1&)
'' __Z7proc_t2R13SomeOtherName => proc_t2(SomeOtherName&)
Code: Select all
extern "c++"
sub proc_signed_char( byval c as byte )
end sub
sub proc_unsigned_char( byval c as ubyte )
end sub
sub proc_char( byval c as ubyte alias "char")
end sub
end extern
'' mangled name => c++ name
'' __Z16proc_signed_chara => proc_signed_char(signed char)
'' __Z18proc_unsigned_charh => proc_unsigned_char(unsigned char)
'' __Z9proc_charc => proc_char(char)
Re: Wiki improvements
Sort of ... there is a specific case that is required on windows.
From ALIAS (modifier):
On Win 64-bit targets, FB to c/c++:
integer on 64-bit targets is 64-bits wide. However, on Win target, c/c++'s long int type is 32-bit, not 64-bit, and we can't use the long long int mangling because it's already used by FB's longint type. Reusing the same mangling (decoration) for two different data types would cause function overloading to fail or have duplicate definitions. To preserve FB's behaviour that Integer on 64-bit targets is always 64-bits, we mangle (decorate) the symbol with a custom datatype and keep the size at 64-bit.To create a data type in FB that will map to c/c++'s long [int] 32-bit on win, we must use alias modifier.
- 64-bit integer maps to custom INTEGER
- 64-bit uinteger maps to custom UINTEGER
- 32-bit long alias "long" maps to long [int]
- 32-bit ulong alias "long" maps to unsigned long [int]
Re: Wiki improvements
Vanya
For your code to work here (win 10), I need
extern "C" {int func(int q1 , int q2);}
in the c++ code.
And I omit
exrtern "C++"
end extern
in the fb code.
And I can leave
type test2 as Long as it is in the fb code.
Win 10.
tested 64 bits,
gcc version 12.1.0 (MinGW-W64 x86_64-posix-seh, built by Brecht Sanders.
This agrees with fbfile.o
For your code to work here (win 10), I need
extern "C" {int func(int q1 , int q2);}
in the c++ code.
And I omit
exrtern "C++"
end extern
in the fb code.
And I can leave
type test2 as Long as it is in the fb code.
Win 10.
tested 64 bits,
gcc version 12.1.0 (MinGW-W64 x86_64-posix-seh, built by Brecht Sanders.
This agrees with fbfile.o
Code: Select all
#inclib "stdc++"
declare function demangle cdecl alias "__cxa_demangle"(as zstring ptr,as zstring ptr=0,as long=0,byref as long=0) as zstring ptr
function getdemangledname(mn as string) as string
dim as long k
dim as string z=*demangle(mn,0,0,k)
print "Demangling: ";iif(len(z)=0,"Fail","OK")
select case k
case 0:print "The demangling operation succeeded."
case -1:print "A memory allocation failiure occurred."
case -2:print "mangled_name is not a valid name under the C++ ABI mangling rules."
case -3:print "One of the arguments is invalid."
end select
return z
end function
Function savefile(filename As String,p As String) As String
Dim As Long n=Freefile
If Open (filename For Binary Access Write As #n)=0 Then
Put #n,,p
Close
Else
Print "Unable to save " + filename:Sleep:End
End If
Return filename
End Function
Function loadfile(file As String) As String
Dim As Long f=Freefile
If Open (file For Binary Access Read As #f)=0 Then
Dim As String text
If Lof(f) > 0 Then
text = String(Lof(f), 0)
Get #f, , text
End If
Close #f
Return text
Else
Print file;" not found":Sleep:End
End If
End Function
function getmangledname(cppproc As String) as string
color 3
Kill "mangle.o"
savefile("mangle.cpp",cppproc)
Print "From file, c++ function name: ";
color 15
Print loadfile("mangle.cpp")
color 3
Shell "g++ -c " +Curdir+ "\mangle.cpp "
Var f= loadfile("mangle.o")
Var m= Mid(f,Instr(f,"_Z"))
Var dist=Instr(m,Chr(0))
m=Mid(m,1,dist)
Print "From .o file, mangled name: ";
color 15
Print m
Kill "mangle.cpp"
Kill "mangle.o"
return m
End function
Dim As String cppproc="int func(int q1 , int q2){return 0;}" '<<---- c++ function
dim as string answer
answer=getmangledname(cppproc)
print getdemangledname(answer)
sleep
Re: Wiki improvements
Code: Select all
For your code to work here (win 10), I need
extern "C" {int func(int q1 , int q2);}
in the c++ code.
-----------
CoderJeff thanks for the detailed answer and examples!
And anyway, thank you all for your help in understanding the issue!
Re: Wiki improvements
@Jeff,
Following your last change (allow named inner types and unions), I think it would be useful for me to have a download file to obtain this new version fbc 1.10 (Windows) so I can update the documentation properly (including examples).
This could take the form of an update to your previous patch of July 16, 2022 (http://www.execulink.com/~coder/freebasic/builds.html).
Thanks in advance.
Following your last change (allow named inner types and unions), I think it would be useful for me to have a download file to obtain this new version fbc 1.10 (Windows) so I can update the documentation properly (including examples).
This could take the form of an update to your previous patch of July 16, 2022 (http://www.execulink.com/~coder/freebasic/builds.html).
Thanks in advance.
Re: Wiki improvements
Thanks.