packed records' address again
Gale Paeper
gpaeper at empirenet.com
Thu Feb 5 17:59:24 CET 2004
Francesco Bonomi wrote:
>
[snip]
> This single one is not allowed:
> r.many_rec[1].arr:=c;
>
Francesco Bonomi wrote:
[snip]
> This assignment fails:
>
> DATA.IDX[H1].KEY:= <array of char>;
[snip]
> I cannot really understand why (and if) this should be safer (from the
> compiler's poin of view) than doing
> DATA.IDX[H1].KEY:= <array of char>;
>
> Any thought?
Regardless of all the jaw flapping about how one shouldn't use packed
data types, the compiler is broke in this area.
To investigate your problem, I tried a few test programs to see what
might be wrong. To keep all the various non-standard extensions out of
the picture, I compiled in Extended Pascal compliance mode. For the
following program:
program CharArrayTest(input, output);
{$extended-pascal}
type
char_arr = array[1..30] of char;
smallrec = RECORD
arr : char_arr;
END;
largerec = packed RECORD
one_rec : smallrec;
many_rec : array[1..5] of smallrec;
one_array : char_arr;
many_arrays : array[1..5] of char_arr;
END;
VAR
r: largerec;
c, c1: char_arr;
aSmallrec: smallrec;
aSmallrecArray: array[1..5] of smallrec;
i: integer;
begin
for i := 1 to 30 do
c[i] := chr(i);
c1 := c;
aSmallrec.arr := c;
aSmallrecArray[1].arr := c;
end.
I got these totally bogus errors when trying to compile:
CharArrayTest.pas: In main program:
CharArrayTest.pas:28: error: using unpacked character arrays as strings
is an extension
CharArrayTest.pas:28: error: of Borland Pascal
CharArrayTest.pas:28: error: using unpacked character arrays as strings
is an extension
CharArrayTest.pas:28: error: of Borland Pascal
CharArrayTest.pas:29: error: using unpacked character arrays as strings
is an extension
CharArrayTest.pas:29: error: of Borland Pascal
CharArrayTest.pas:29: error: using unpacked character arrays as strings
is an extension
CharArrayTest.pas:29: error: of Borland Pascal
CharArrayTest.pas:30: error: using unpacked character arrays as strings
is an extension
CharArrayTest.pas:30: error: of Borland Pascal
CharArrayTest.pas:30: error: using unpacked character arrays as strings
is an extension
CharArrayTest.pas:30: error: of Borland Pascal
The errors are totally bogus because there are abolutely no strings in
the program and there is nothing requiring string semantics in the
program. Per ISO 7185/10206, since there is no 'packed' token in the
declaration of the char_arr type, the char_arr type is a plain old array
type with char type elements. Since all the assignments have exactly
the same type on the left hand and right hand sides (char type or
char_arr type which is array type with char element types), they are
completely assignment compatible per ISO 7185/10206 paragraph 6.4.6 a).
To get around these bogus errors, the following program uses packed to
force a string type:
program PackedCharArrayTest(input, output);
{$extended-pascal}
type
char_arr = packed array[1..30] of char;
smallrec = RECORD
arr : char_arr;
END;
largerec = packed RECORD
one_rec : smallrec;
many_rec : array[1..5] of smallrec;
one_array : char_arr;
many_arrays : array[1..5] of char_arr;
END;
VAR
r: largerec;
c, c1: char_arr;
aSmallrec: smallrec;
aSmallrecArray: array[1..5] of smallrec;
i: integer;
begin
for i := 1 to 30 do
c[i] := chr(i);
c1 := c;
aSmallrec.arr := c;
aSmallrecArray[1].arr := c;
r.many_rec[1].arr := c; {compiler error but ISO7185/10206 legal}
end.
And I got the same error you've been wrestling with:
PackedCharArrayTest.pas: In main program:
PackedCharArrayTest.pas:31: error: cannot take address of packed record
field `many_rec'
Again this is a bogus error. The assignment statememt
"r.many_rec[1].arr := c;" is fully compliant with all requirements of
ISO 7185/10206. The type of "r.many_rec[1].arr" is fixed-string-type
with a capacity of 30 and "c" is fixed-string-type with capacity and
length both 30 so per ISO 7185/10206 paragraph 6.4.6 f) and ISO 10206
paragraph 6.9.2.2 (6.8.2.2 for ISO 7185) the assignment statement is
fully compliant with ISO requirements.
I will note that ISO 7185/10206 puts one extra restriction and ONLY one
extra restriction on the usage of a variable of packed type (including
string types which are or contain packaged array types). From ISO
10206, paragraph 6.7.3.3:
"An actual variable parameter shall not denote a component of a variable
where that variable possesses a type that is
designated packed. An actual variable parameter shall not denote a
component of a string-type."
However, that requirement doesn't even apply to "r.many_rec[1].arr"
since the "arr" field is NOT a packed type compontent. Per ISO 10206.
paragraph 6.4.3.1:
"The designation of a structured-type as packed shall affect the
representation in data-storage of that structured-type only; i.e., if a
component is itself structured, the component's representation in
data-storage shall be packed only if the type of the component is
designated packed."
In other words, even though the largerec type is designated "packed",
the "arr" field isn't a packed field because the smallrec type has NOT
been designated "packed".
Regardless of the wisdom of using packed data types, the compiler has at
least two bugs in the area of character arrays which are ISO 7185/10206
compliance failures. Therefore, those bugs need to be fix.
Russell Whitaker wrote:
> 1. "packed array [ ] of char" is not a string.
You're mistaken on this given the context of the discussion. "packed
array [1..N] of char", where N >= 1, is defined to be a
fixed-string-type in ISO 10206 and a string-type (and the only
string-type) in ISO 7185.
> 2. "packed record". Most cpu's handle data on four byte boundrys.
So what? Francesco isn't complaining about performance. Francesco is
complaining about the compiler rejecting a ISO 7185/10206 perfectly
legal assignment statement. Francesco complaint is valid and identifies
a ISO compliance failure in the compiler.
Also, compared to the baroque CDC Cyber 6600 architecture where Wirth
implemented the first Pascal compiler on, today's CPU are pretty much
nirvana for compiler implementors. If Wirth could get decent performace
in assignment statements involving packed data structures on that
machine, surely any compiler implementor worth their salt should be able
to do it on today's architecures.
Gale Paeper
gpaeper at empirenet.com
More information about the Gpc
mailing list