amd64 - function returning record with field straddling 2 registers
gdb/ChangeLog: From Paul Hilfinger <hilfinger@adacore.com> * amd64-tdep.c (amd_classify_aggregate): Handle the case of a record of length <= 16 in which a field straddles the two eightbytes. gdb/testsuite/ChangeLog: * gdb.ada/rec_return: New testcase.
This commit is contained in:
parent
cba6fab54a
commit
e4e2711a4a
@ -1,3 +1,10 @@
|
||||
2010-01-29 Paul Hilfinger <hilfinger@adacore.com>
|
||||
|
||||
amd64 - function returning record with field straddling 2 registers.
|
||||
* amd64-tdep.c (amd_classify_aggregate): Handle the case of
|
||||
a record of length <= 16 in which a field straddles the two
|
||||
eightbytes.
|
||||
|
||||
2010-01-29 Joel Brobecker <brobecker@adacore.com>
|
||||
|
||||
Implement return values on amd64-windows.
|
||||
|
@ -347,6 +347,12 @@ amd64_classify_aggregate (struct type *type, enum amd64_reg_class class[2])
|
||||
struct type *subtype = check_typedef (TYPE_FIELD_TYPE (type, i));
|
||||
int pos = TYPE_FIELD_BITPOS (type, i) / 64;
|
||||
enum amd64_reg_class subclass[2];
|
||||
int bitsize = TYPE_FIELD_BITSIZE (type, i);
|
||||
int endpos;
|
||||
|
||||
if (bitsize == 0)
|
||||
bitsize = TYPE_LENGTH (subtype) * 8;
|
||||
endpos = (TYPE_FIELD_BITPOS (type, i) + bitsize - 1) / 64;
|
||||
|
||||
/* Ignore static fields. */
|
||||
if (field_is_static (&TYPE_FIELD (type, i)))
|
||||
@ -356,6 +362,30 @@ amd64_classify_aggregate (struct type *type, enum amd64_reg_class class[2])
|
||||
|
||||
amd64_classify (subtype, subclass);
|
||||
class[pos] = amd64_merge_classes (class[pos], subclass[0]);
|
||||
if (bitsize <= 64 && pos == 0 && endpos == 1)
|
||||
/* This is a bit of an odd case: We have a field that would
|
||||
normally fit in one of the two eightbytes, except that
|
||||
it is placed in a way that this field straddles them.
|
||||
This has been seen with a structure containing an array.
|
||||
|
||||
The ABI is a bit unclear in this case, but we assume that
|
||||
this field's class (stored in subclass[0]) must also be merged
|
||||
into class[1]. In other words, our field has a piece stored
|
||||
in the second eight-byte, and thus its class applies to
|
||||
the second eight-byte as well.
|
||||
|
||||
In the case where the field length exceeds 8 bytes,
|
||||
it should not be necessary to merge the field class
|
||||
into class[1]. As LEN > 8, subclass[1] is necessarily
|
||||
different from AMD64_NO_CLASS. If subclass[1] is equal
|
||||
to subclass[0], then the normal class[1]/subclass[1]
|
||||
merging will take care of everything. For subclass[1]
|
||||
to be different from subclass[0], I can only see the case
|
||||
where we have a SSE/SSEUP or X87/X87UP pair, which both
|
||||
use up all 16 bytes of the aggregate, and are already
|
||||
handled just fine (because each portion sits on its own
|
||||
8-byte). */
|
||||
class[1] = amd64_merge_classes (class[1], subclass[0]);
|
||||
if (pos == 0)
|
||||
class[1] = amd64_merge_classes (class[1], subclass[1]);
|
||||
}
|
||||
|
@ -1,3 +1,7 @@
|
||||
2010-01-29 Joel Brobecker <brobecker@adacore.com>
|
||||
|
||||
* gdb.ada/rec_return: New testcase.
|
||||
|
||||
2010-01-29 Joel Brobecker <brobecker@adacore.com>
|
||||
|
||||
* gdb.ada/call_pn: New testcase.
|
||||
|
46
gdb/testsuite/gdb.ada/rec_return.exp
Normal file
46
gdb/testsuite/gdb.ada/rec_return.exp
Normal file
@ -0,0 +1,46 @@
|
||||
# Copyright 2010 Free Software Foundation, Inc.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
if $tracelevel then {
|
||||
strace $tracelevel
|
||||
}
|
||||
|
||||
load_lib "ada.exp"
|
||||
|
||||
set testdir "rec_return"
|
||||
set testfile "${testdir}/foo"
|
||||
set srcfile ${srcdir}/${subdir}/${testfile}.adb
|
||||
set binfile ${objdir}/${subdir}/${testfile}
|
||||
|
||||
file mkdir ${objdir}/${subdir}/${testdir}
|
||||
if {[gdb_compile_ada "${srcfile}" "${binfile}" executable [list debug ]] != "" } {
|
||||
return -1
|
||||
}
|
||||
|
||||
gdb_exit
|
||||
gdb_start
|
||||
gdb_reinitialize_dir $srcdir/$subdir
|
||||
gdb_load ${binfile}
|
||||
|
||||
set bp_location [gdb_get_line_number "STOP" ${testdir}/foo.adb]
|
||||
if ![runto "foo.adb:$bp_location" ] then {
|
||||
perror "Couldn't run ${testfile}"
|
||||
return
|
||||
}
|
||||
|
||||
gdb_test "print bar" \
|
||||
"= \\(x => 42, s => \"ABCDEFGH\"\\)" \
|
||||
"print bar"
|
||||
|
24
gdb/testsuite/gdb.ada/rec_return/foo.adb
Normal file
24
gdb/testsuite/gdb.ada/rec_return/foo.adb
Normal file
@ -0,0 +1,24 @@
|
||||
-- Copyright 2010 Free Software Foundation, Inc.
|
||||
--
|
||||
-- This program is free software; you can redistribute it and/or modify
|
||||
-- it under the terms of the GNU General Public License as published by
|
||||
-- the Free Software Foundation; either version 3 of the License, or
|
||||
-- (at your option) any later version.
|
||||
--
|
||||
-- This program is distributed in the hope that it will be useful,
|
||||
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
-- GNU General Public License for more details.
|
||||
--
|
||||
-- You should have received a copy of the GNU General Public License
|
||||
-- along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
with Pck; use Pck;
|
||||
|
||||
procedure Foo is
|
||||
Q: Rec;
|
||||
begin
|
||||
Q := Bar; -- STOP HERE
|
||||
Do_Nothing (Q'Address);
|
||||
end Foo;
|
||||
|
27
gdb/testsuite/gdb.ada/rec_return/pck.adb
Normal file
27
gdb/testsuite/gdb.ada/rec_return/pck.adb
Normal file
@ -0,0 +1,27 @@
|
||||
-- Copyright 2010 Free Software Foundation, Inc.
|
||||
--
|
||||
-- This program is free software; you can redistribute it and/or modify
|
||||
-- it under the terms of the GNU General Public License as published by
|
||||
-- the Free Software Foundation; either version 3 of the License, or
|
||||
-- (at your option) any later version.
|
||||
--
|
||||
-- This program is distributed in the hope that it will be useful,
|
||||
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
-- GNU General Public License for more details.
|
||||
--
|
||||
-- You should have received a copy of the GNU General Public License
|
||||
-- along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
package body Pck is
|
||||
function Bar return Rec is
|
||||
begin
|
||||
return (X => 42, S => "ABCDEFGH");
|
||||
end Bar;
|
||||
|
||||
procedure Do_Nothing (A : System.Address) is
|
||||
begin
|
||||
null;
|
||||
end Do_Nothing;
|
||||
end Pck;
|
||||
|
28
gdb/testsuite/gdb.ada/rec_return/pck.ads
Normal file
28
gdb/testsuite/gdb.ada/rec_return/pck.ads
Normal file
@ -0,0 +1,28 @@
|
||||
-- Copyright 2010 Free Software Foundation, Inc.
|
||||
--
|
||||
-- This program is free software; you can redistribute it and/or modify
|
||||
-- it under the terms of the GNU General Public License as published by
|
||||
-- the Free Software Foundation; either version 3 of the License, or
|
||||
-- (at your option) any later version.
|
||||
--
|
||||
-- This program is distributed in the hope that it will be useful,
|
||||
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
-- GNU General Public License for more details.
|
||||
--
|
||||
-- You should have received a copy of the GNU General Public License
|
||||
-- along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
with System;
|
||||
|
||||
package Pck is
|
||||
type Rec is record
|
||||
X: Integer;
|
||||
S: String (1..8);
|
||||
end record;
|
||||
|
||||
function Bar return Rec;
|
||||
procedure Do_Nothing (A : System.Address);
|
||||
|
||||
end Pck;
|
||||
|
Loading…
Reference in New Issue
Block a user