[fpc-pascal]Compiler Bug--ansistrings
Mark Emerson
ChiefAngel at angelbase.com
Sat Apr 26 05:31:49 CEST 2003
I found the following compiler bug involving ansistrings, running FPC
under Linux. The program is called bug, and it references a unit called
bug_unit. Both appear below.
The bug_unit contains a couple of "irrelevant" declarations that remain
after I removed masses of stuff to narrow down the bug. More on them below.
Note that procedure test in the unit is identical to procedure test1 in
the program, except for its name. Note also that BOTH procedures
involve appending a null character to an ansistring.
Now, as you will see, appending the null character WORKS in test1, but
causes a runtime error (216) in the unit.
If chr(0) is changed to any other char, such as chr(1), in the unit, the
program runs successfully.
Alternatively, if chr(0) is KEPT in the unit, but instead the
"irrelevant" procedure called tab_delim_escapes_to_chars is commented
out, then, once again, the program runs successfully.
We are currently having a far more difficult problem with ansistrings,
but I'm not in a position to report it yet, as it involves masses of code.
I LOVE this compiler. Please fix it! :)
Mark Emerson
http://angelbase.com/pascal/
program bug;
uses bug_unit;
var s : ansistring;
function test1 (item : ansistring) : ansistring;
begin
WRITELN ('TEST1 ITEM=', ITEM);
TEST1 := item + chr(0);
end;
begin
writeln (test1 ('abc'));
writeln (test ('abc'));
end.
unit bug_unit;
interface
function test (item : ansistring) : ansistring;
{=== Miscellaneous stuff ===}
type
char_set_type = set of char;
natural = cardinal;
const
endsource_char = chr(255);
tab_delim_char_codes = [9, 10, 13];
letters_set_const = ['A'..'Z', 'a'..'z'];
digits_set_const = ['0'..'9'];
white_space_set_const = [' ', chr(9), chr(10), chr(13)];
CRLF = chr(13)+chr(10);
{========================}
implementation
{=== STUBS TO REMOVE ===}
procedure error (error_msg : ansistring);
begin
writeln ('error_msg');
halt;
end;
function tab_delim_escapes_to_chars (s : ansistring) : ansistring;
{going left to right, replaces \009, \010 and \013 with
chr(9), chr(10), and chr (13) respectively.}
var
esc_i : longint;
len : natural;
j : natural;
esc_str : string[3];
esc_val : word;
got_esc : boolean;
begin
len := length (s);
if len > 3 then
for esc_i := len-3 downto 1 do
if s[esc_i] = '\' then begin
esc_str := '';
got_esc := false;
if esc_i + 3 <= length (s) then begin
got_esc := true;
for j := esc_i + 1 to esc_i + 3 do
if not (s[j] in digits_set_const)
then got_esc := false;
end;
if got_esc then begin
esc_str := copy (s, esc_i+1, 3);
val (esc_str, esc_val);
if esc_val in tab_delim_char_codes then
s := copy (s, 1, esc_i-1) + chr (esc_val) +
copy (s, esc_i+4, len);
end;
end;
tab_delim_escapes_to_chars := s;
end;
function test (item : ansistring) : ansistring;
begin
WRITELN ('TEST ITEM=', ITEM);
TEST := item + chr(0);
end;
end.
More information about the fpc-pascal
mailing list