regarding GIT, i (at least intentionally) didn´t change anything else than some files in the compiler folder. The .jkp file is the project file for my IDE i obviously forgot to add to the ignore list. So please turn down all other changes.
I see now it is due to the added
.gitattributes and your local machine probably has the default system wide setting of core.autocrlf=false. To work better with the fbc sources on multiple platforms, it is better (for the fbc source tree in particular) to have this set to core.autocrlf=true. Line endings will automatically be converted to CRLF for all files on windows (LF on linux). There's only a couple places in the source tree that we force LF line endings.
Also, fbc source mostly has TAB character for indent. Comments for statements on the line above (not in line or at end of line). And no need for long
'' --- * 70 comment breaks.
>> then just modify the AST expr.
>I actually don´t change the expr, i just redirect the code flow, based on the fact that one of our UDTs is recognized (by it´s name for now).
>>Avoid the GOTO's, some of them are skipping over DIM statements.
> But the alternative would be to make major changes in code structure and thus potentially breaking things
You are making it really hard on your self, and me trying to read your code. Have a look at
https://github.com/jayrm/fbc/commits/udt-wstring specifically in rtl-string.bas. 50 lines changed instead of 500.
Better would be to use #pragma push/pop
> but what for is #pragma push/pop?
Push/Pop, or assignment, allows to turn the new behaviour on and off within the same source code.
>>attach the "UDT-is-a-Wstring" flag to the UDT's type-def[/quote]
> Which would require some new syntax for specifying this flag. Why not just check for "can-cast-as-wstring", which would have the same effect without the need for any syntax change/addition.
I agree. There should be no need to check for special names (it slows down the compiler). Attaching "can-cast-as-wstring" flag to the UDT can help speed up the compiler if the check is made often.
>
For a schedule i would propose these steps:>1.) make sure, that, what we have now, really works FLAWLESSLY for Windows, LINUX and maybe other targets, which can deal with wide strings.
Where are your test files? What source you are using to check that your changes work?
> 2.) integrate this into the next official release, maybe with #2 of your list, maybe without it. This is a timing thing: when will be the next release, and how much time will it need to get #2 tested and implemented?
"fixing UDT implicit casting for built in [w]string rtlib functions", which is what you've been working on? The #pragma tells fbc to prefer casting to WSTRING type if it is a UDT, rather than STRING type which fbc does by default. That's a pretty good solution, especially if you are building UNICODE only programs.
> 3.) solve #2 and #3 of your list.
The problems of #3 will be noticed with respect to strings when a UDT has both cast to wstring and string. However, if we have fbc just prefer one or the other, there's no ambiguity for the built in run time functions. Though the problem still exists.
> 4.) make USTRING a built-in type (#1 of your list). Personally i can live with fact of having to include an extra file for dynamic wide strings, so it is last in my personal priority and my schedule. What do you think?
Yes, later.
----
in
https://github.com/jayrm/fbc/commits/udt-wstring - I (re)added the pragma as push/pop
- made some changes to rtl-string.bas
- I didn't look much in to the other additions you are making, as I have no idea what the cases are that you are fixing.
For example, here is a test I created for the few additions that I made (sorry, macro abuse):
#include once "../WinFBX/Afx/CWStr.inc"
#pragma udt_wstring=true
type some_wide_string as CWStr
private function EscapeUnicodeToAscii _
( _
byref w as const wstring _
) as string
dim ret as string
for i as integer = 0 to len(w)-1
select case w[i]
case 9
ret &= "\t"
case 32 to 127
ret &= chr(w[i])
case else
ret &= "\u" & hex(w[i],sizeof(wstring)*2)
end select
next
function = ret
end function
private sub wcheck overload _
( _
byref tag as const string, _
byref expr as const string, _
byref a as const wstring, _
byref b as const wstring _
)
dim fail as boolean
print tag & ", " & expr & ": ";
if( len(a) <> len(b) ) then
print !"Failed!: length does not match"
fail = true
elseif( a <> b ) then
print !"Failed!: not matched"
fail = true
else
print !"OK"
end if
if( fail ) then
print !"\tA: """ & EscapeUnicodeToAscii( a ) & """"
print !"\tB: """ & EscapeUnicodeToAscii( b ) & """"
end 1
end if
print
end sub
private sub wcheck overload _
( _
byref tag as const string, _
byref expr as const string, _
byval a as const integer, _
byval b as const integer _
)
print tag & ", " & expr & ": ";
if( a = b ) then
print !"OK"
else
print !"Failed"
end if
print
end sub
#macro t( expr )
#define Xexpr(X) expr
a2 = Xexpr(a1)
b2 = Xexpr(b1)
wcheck( "A=B", #expr, a2, b2 )
wcheck( "f(A)=f(B)", #expr, Xexpr(a2), Xexpr(b2) )
wcheck( "f(A)=f(**B)", #expr, Xexpr(a2), Xexpr(**b2) )
#undef Xexpr
#endmacro
#macro t_int( expr )
#define Xexpr(X) expr
a_int = Xexpr(a1)
b_int = Xexpr(b1)
c_int = Xexpr(c1)
wcheck( "f(A)=f(B)", #expr, a_int, b_int )
wcheck( "f(A)=f(**B)", #expr, a_int, c_int )
#undef Xexpr
#endmacro
private sub do_test _
( _
byref text as const wstring _
)
dim a1 as wstring * 40 = text
dim b1 as some_wide_string = text
dim c1 as wstring * 40 = **b1
dim a2 as wstring * 40
dim b2 as some_wide_string
dim a_int as integer
dim b_int as integer
dim c_int as integer
t( left( X, 3 ) )
t( right( X, 3 ) )
t( ltrim( X ) )
t( rtrim( X ) )
t( trim( X ) )
t( ltrim( X, any !" \t" ) )
t( rtrim( X, any !" \t" ) )
t( trim( X, any !" \t" ) )
t( mid( X, 2 ) )
t( mid( X, 3 ) )
t( mid( X, 2, 3 ) )
t( mid( X, 4, 6 ) )
t( lcase( X ) )
t( ucase( X ) )
t_int( asc( X ) )
t_int( instr( X, !"\u304B" ) )
t_int( instr( X, !"not-here" ) )
t_int( instr( X, !"Hel" ) )
t_int( instr( X, !"\u3055\u3093" ) )
t_int( instrrev( X, !"\u304B" ) )
t_int( instrrev( X, !"not-here" ) )
t_int( instrrev( X, !"Hel" ) )
t_int( instrrev( X, !"\u3055\u3093" ) )
end sub
do_test( !"Hello \u304A\u304B\u3042\u3055\u3093" )
do_test( !" Hello \u304A\u304B\u3042\u3055\u3093 " )
do_test( !" \tHello \u304A\u304B\u3042\u3055\u3093\t " )
do_test( !" \u3042 " )
do_test( !"\u3042" )
I wrote the test this way so I can inspect the results on any dumb ascii terminal, and can convert to fbc's test-suite later. Anything you change or add, you should have a test in mind, that can be automated.