From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 17812 invoked by alias); 9 Jan 2008 06:34:32 -0000 Received: (qmail 17803 invoked by uid 22791); 9 Jan 2008 06:34:31 -0000 X-Spam-Check-By: sourceware.org Received: from rock.gnat.com (HELO rock.gnat.com) (205.232.38.15) by sourceware.org (qpsmtpd/0.31) with ESMTP; Wed, 09 Jan 2008 06:33:53 +0000 Received: from localhost (localhost.localdomain [127.0.0.1]) by filtered-rock.gnat.com (Postfix) with ESMTP id C62F52A96A8 for ; Wed, 9 Jan 2008 01:33:51 -0500 (EST) Received: from rock.gnat.com ([127.0.0.1]) by localhost (rock.gnat.com [127.0.0.1]) (amavisd-new, port 10024) with LMTP id 8ZQtC18j3maQ for ; Wed, 9 Jan 2008 01:33:51 -0500 (EST) Received: from joel.gnat.com (localhost.localdomain [127.0.0.1]) by rock.gnat.com (Postfix) with ESMTP id A3BEB2A96A7 for ; Wed, 9 Jan 2008 01:33:49 -0500 (EST) Received: by joel.gnat.com (Postfix, from userid 1000) id 36AEDE7ACB; Tue, 8 Jan 2008 22:33:42 -0800 (PST) Date: Wed, 09 Jan 2008 06:34:00 -0000 From: Joel Brobecker To: gdb-patches@sourceware.org Subject: [RFA] Add handling of null Ada arrays Message-ID: <20080109063342.GE20580@adacore.com> Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="cvVnyQ+4j833TQvp" Content-Disposition: inline User-Agent: Mutt/1.4.2.2i Mailing-List: contact gdb-patches-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sourceware.org X-SW-Source: 2008-01/txt/msg00174.txt.bz2 --cvVnyQ+4j833TQvp Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-length: 1019 Hello, In Ada, arrays can be empty by setting the high bound to a smaller value than the low bound. For instance, a typical declaration would be: type Empty_Array is array (1 .. 0) of Integer; The attached patch fixes a bug when trying to print a variable of such a type: (gdb) print my_table object size is larger than varsize-limit The problem is that we compute the array length using the bounds from the index type without checking first that the high bound is larger or equal to the small bound. There were a couple of places were we did that, so we made some adjustments there. 2008-01-09 Joel Brobecker * gdbtypes.c (create_array_type): Add handling of null Ada arrays. (check_typedef): Likewise. I was able to write a testcase too: 2008-01-09 Joel Brobecker * gdb.ada/null_array: New test program. * gdb.ada/null_array.exp: New testcase. Tested on x86-linux, no regression. OK to commit? Thanks, -- Joel --cvVnyQ+4j833TQvp Content-Type: text/plain; charset=us-ascii Content-Disposition: attachment; filename="null_array.diff" Content-length: 1908 Index: gdbtypes.c =================================================================== --- gdbtypes.c (revision 113) +++ gdbtypes.c (revision 116) @@ -811,8 +811,14 @@ create_array_type (struct type *result_t if (get_discrete_bounds (range_type, &low_bound, &high_bound) < 0) low_bound = high_bound = 0; CHECK_TYPEDEF (element_type); - TYPE_LENGTH (result_type) = - TYPE_LENGTH (element_type) * (high_bound - low_bound + 1); + /* Be careful when setting the array length. Ada arrays can be + empty arrays with the high_bound being smaller than the low_bound. + In such cases, the array length should be zero. */ + if (high_bound < low_bound) + TYPE_LENGTH (result_type) = 0; + else + TYPE_LENGTH (result_type) = + TYPE_LENGTH (element_type) * (high_bound - low_bound + 1); TYPE_NFIELDS (result_type) = 1; TYPE_FIELDS (result_type) = (struct field *) TYPE_ALLOC (result_type, sizeof (struct field)); @@ -1492,11 +1498,19 @@ check_typedef (struct type *type) == TYPE_CODE_RANGE)) { /* Now recompute the length of the array type, based on its - number of elements and the target type's length. */ - TYPE_LENGTH (type) = - ((TYPE_FIELD_BITPOS (range_type, 1) - - TYPE_FIELD_BITPOS (range_type, 0) + 1) - * TYPE_LENGTH (target_type)); + number of elements and the target type's length. + Watch out for Ada null Ada arrays where the high bound + is smaller than the low bound. */ + const int low_bound = TYPE_FIELD_BITPOS (range_type, 0); + const int high_bound = TYPE_FIELD_BITPOS (range_type, 1); + int nb_elements; + + if (high_bound < low_bound) + nb_elements = 0; + else + nb_elements = high_bound - low_bound + 1; + + TYPE_LENGTH (type) = nb_elements * TYPE_LENGTH (target_type); TYPE_FLAGS (type) &= ~TYPE_FLAG_TARGET_STUB; } else if (TYPE_CODE (type) == TYPE_CODE_RANGE) --cvVnyQ+4j833TQvp Content-Type: text/plain; charset=us-ascii Content-Disposition: attachment; filename="null_array-tc.diff" Content-length: 5097 Index: gdb.ada/null_array.exp =================================================================== --- gdb.ada/null_array.exp (revision 0) +++ gdb.ada/null_array.exp (revision 115) @@ -0,0 +1,50 @@ +# Copyright 2008 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 . + +if $tracelevel then { + strace $tracelevel +} + +load_lib "ada.exp" + +set testdir "null_array" +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 "START" ${testdir}/foo.adb] +runto "foo.adb:$bp_location" + +# Test printing and type-printing of a tagged type that is not +# class-wide. + +gdb_test "print my_table" \ + "\\(\\)" \ + "print my_table" + +gdb_test "ptype my_table" \ + "type = array \\(10 \\.\\. 1\\) of integer" \ + "ptype my_table" + Index: gdb.ada/null_array/pck.adb =================================================================== --- gdb.ada/null_array/pck.adb (revision 0) +++ gdb.ada/null_array/pck.adb (revision 115) @@ -0,0 +1,28 @@ +-- Copyright 2008 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 . + +package body Pck is + + function Ident (I : Integer) return Integer is + begin + return I; + end Ident; + + procedure Do_Nothing (A : System.Address) is + begin + null; + end Do_Nothing; + +end Pck; Index: gdb.ada/null_array/pck.ads =================================================================== --- gdb.ada/null_array/pck.ads (revision 0) +++ gdb.ada/null_array/pck.ads (revision 115) @@ -0,0 +1,24 @@ +-- Copyright 2008 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 . + +with System; + +package Pck is + + function Ident (I : Integer) return Integer; + + procedure Do_Nothing (A : System.Address); + +end Pck; Index: gdb.ada/null_array/foo.adb =================================================================== --- gdb.ada/null_array/foo.adb (revision 0) +++ gdb.ada/null_array/foo.adb (revision 115) @@ -0,0 +1,24 @@ +-- Copyright 2008 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 . + +with Pck; use Pck; + +procedure Foo is + type Table is array (Integer range <>) of Integer; + + My_Table : Table (Ident (10) .. Ident (1)); +begin + Do_Nothing (My_Table'Address); -- START +end Foo; --cvVnyQ+4j833TQvp--