From patchwork Thu Oct 31 21:55:41 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Georg-Johann Lay X-Patchwork-Id: 1187685 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=209.132.180.131; helo=sourceware.org; envelope-from=gcc-patches-return-512200-incoming=patchwork.ozlabs.org@gcc.gnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=gjlay.de Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=gcc.gnu.org header.i=@gcc.gnu.org header.b="wPfYidtG"; dkim=fail reason="signature verification failed" (2048-bit key; unprotected) header.d=gjlay.de header.i=@gjlay.de header.b="GuN/Rtvj"; dkim-atps=neutral Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 473zh35NqHz9sP4 for ; Fri, 1 Nov 2019 08:57:21 +1100 (AEDT) DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :message-id:date:from:mime-version:to:cc:subject:content-type; q=dns; s=default; b=UcseIoSWzkOMcQNgc2esMcmfNUaJOHWupEGwYoPGvvo ZbJnhmtoS1ETYWWSvgmoJcFO6bAqUZTMxFam9SFJu4w9Zh9fu01imXfI4afBaWez nOKirC6q2VawgkAYhV6oPB7wVWzNo/hTuxIiImGE7az9PSLrSSmFPdEl9d89aQtw = DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :message-id:date:from:mime-version:to:cc:subject:content-type; s=default; bh=Ko0uebgYklkNnaD3gEs1QzTGEsY=; b=wPfYidtGIJvUz/FXq JNCeQkP+ctcMh1gPtNmnqrbBdZYCBTIgw6/NR1Gkj8xV7S07478nQn/n1P7IDjaN Io54wZ/83G2RMs1LEtXrQzWSPgHFv8MGLSjyscweythqICtv8V455vFzEnl7cWD8 7KyLPCCAR38gDy9B0OAWJ0PsJY= Received: (qmail 93226 invoked by alias); 31 Oct 2019 21:57:12 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Received: (qmail 93212 invoked by uid 89); 31 Oct 2019 21:57:12 -0000 Authentication-Results: sourceware.org; auth=none X-Spam-SWARE-Status: No, score=-9.7 required=5.0 tests=AWL, BAYES_00, GIT_PATCH_1, GIT_PATCH_2, GIT_PATCH_3, KAM_ASCII_DIVIDERS, KAM_SHORT, RCVD_IN_DNSWL_NONE, SPF_HELO_PASS autolearn=ham version=3.3.1 spammy=lim, LIM, sk:MULTILI, sk:multili X-HELO: mo4-p00-ob.smtp.rzone.de Received: from mo4-p00-ob.smtp.rzone.de (HELO mo4-p00-ob.smtp.rzone.de) (81.169.146.217) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Thu, 31 Oct 2019 21:57:07 +0000 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; t=1572559025; s=strato-dkim-0002; d=gjlay.de; h=Subject:CC:To:From:Date:Message-ID:X-RZG-CLASS-ID:X-RZG-AUTH:From: Subject:Sender; bh=YvZw4h5DJ5O7+XaJTKDXYWZy7zPWxkfnnS4E0PLz7eE=; b=GuN/Rtvj4m/maoTGxW8YQXPo7bNHJyvPPfCbMAz9We+7zGHvbN/5j3+Sc52CB1WTnZ NYoJ+rm7+gwQzPN+q775PtAqO6NjiD1YLL1ufA4HBEsdMG25Vjx6yzAD/Gw1DJyRPplK wAaGpSMYYsQq0C6wuV2lgFk6wm85DDMUD9x7ungUjVitn7qZEiESEJDq317Ewomja0JH Bo6E69EBfMoDcYaML/q6/n6q3jVY6QtaJ3G1V3Z0dI50Es+Z4PIdhO/Ogc/nPmr/UfvZ WNn89txZs6hDLLGSs3kx0FSCkAowvl1UlP7tpk+VpJtQ+sSGphAwXpWtjA+yxKYn/E2w W1CQ== Received: from [192.168.2.100] by smtp.strato.de (RZmta 44.29.0 DYNA|AUTH) with ESMTPSA id z06ddev9VLuu77s (using TLSv1 with cipher ECDHE-RSA-AES256-SHA (curve secp521r1 with 521 ECDH bits, eq. 15360 bits RSA)) (Client did not present a certificate); Thu, 31 Oct 2019 22:56:56 +0100 (CET) Message-ID: <5DBB585D.1090108@gjlay.de> Date: Thu, 31 Oct 2019 22:55:41 +0100 From: Georg-Johann Lay User-Agent: Thunderbird 2.0.0.24 (Windows/20100228) MIME-Version: 1.0 To: GCC Patches CC: Jeff Law , Denis Chertykov Subject: [patch][avr] PR92055: Add switches to enable 64-bit [long] double. X-IsSubscribed: yes Hi, this adds the possibility to enable IEEE compatible double and long double support in avr-gcc. It supports 2 configure options --with-double={32|64|32,64|64,32} --with-long-double={32|64|32,64|64,32|double} which select the default layout of these types and also chose which mutlilib variants are built and available. These two config option map to the new compiler options -mdouble= and -mlong-double= which are new multilib options. The patch only deals with option handling and multilib bits, it does not add any double functionality. The double support functions are supposed to be provided by avr-libc which also hosts all the float stuff, including __addsf3 etc. Ok for trunk? Johann gcc/ Support 64-bit double and 64-bit long double configurations. PR target/92055 * config.gcc (tm_defines) [avr]: Set from --with-double=, --with-long-double=. * config/avr/t-multilib: Remove. * config/avr/t-avr: Output of genmultilib.awk is now fully dynamically generated and no more part of the repo. (HAVE_DOUBLE_MULTILIB, HAVE_LONG_DOUBLE_MULTILIB): New variables. Pass them down to... * config/avr/genmultilib.awk: ...here and handle them. * gcc/config/avr/avr.opt (-mdouble=, avr_double). New option and var. (-mlong-double=, avr_long_double). New option and var. * common/config/avr/avr-common.c (opts.h): Include. (diagnostic.h): Include. (TARGET_OPTION_OPTIMIZATION_TABLE) <-mdouble=>: Set default as requested by --with-double=. <-mlong-double=>: Set default as requested by --with-long-double=. (TARGET_OPTION_OPTIMIZATION_TABLE) <-mdouble=, -mlong-double=>: Set default as requested by --with-double= (TARGET_HANDLE_OPTION): Define to this... (avr_handle_option): ...new hook worker. * config/avr/avr.h (DOUBLE_TYPE_SIZE): Define to avr_double. (LONG_DOUBLE_TYPE_SIZE): Define to avr_long_double. (avr_double_lib): New proto for spec function. (EXTRA_SPEC_FUNCTIONS) <double-lib>: Add. (DRIVER_SELF_SPECS): Call %:double-lib. * config/avr/avr.c (avr_option_override): Assert sizeof(long double) >= sizeof(double) for the target. * config/avr/avr-c.c (avr_cpu_cpp_builtins) [__HAVE_DOUBLE_MULTILIB__, __HAVE_LONG_DOUBLE_MULTILIB__] [__HAVE_DOUBLE64__, __HAVE_DOUBLE32__, __DEFAULT_DOUBLE__=] [__HAVE_LONG_DOUBLE64__, __HAVE_LONG_DOUBLE32__] [__HAVE_LONG_DOUBLE_IS_DOUBLE__, __DEFAULT_LONG_DOUBLE__=]: New built-in defined depending on --with-double=, --with-long-double=. * config/avr/driver-avr.c (avr_double_lib): New spec function. * doc/invoke.tex (AVR Options) <-mdouble=,-mlong-double=>: Doc. libgcc/ Support 64-bit double and 64-bit long double configurations. PR target/92055 * config/avr/t-avr (HOST_LIBGCC2_CFLAGS): Only add -DF=SF if long double is a 32-bit type. * config/avr/t-avrlibc: Copy double64 and long-double64 multilib(s) from the vanilla one. * config/avr/t-copy-libgcc: New Makefile snip. Index: gcc/common/config/avr/avr-common.c =================================================================== --- gcc/common/config/avr/avr-common.c (revision 277236) +++ gcc/common/config/avr/avr-common.c (working copy) @@ -23,6 +23,8 @@ #include "tm.h" #include "common/common-target.h" #include "common/common-target-def.h" +#include "opts.h" +#include "diagnostic.h" /* Implement TARGET_OPTION_OPTIMIZATION_TABLE. */ static const struct default_options avr_option_optimization_table[] = @@ -43,9 +45,97 @@ static const struct default_options avr_ performance decrease. For the AVR though, disallowing data races introduces additional code in LIM and increases reg pressure. */ { OPT_LEVELS_ALL, OPT_fallow_store_data_races, NULL, 1 }, + +#if defined (WITH_DOUBLE64) + { OPT_LEVELS_ALL, OPT_mdouble_, NULL, 64 }, +#elif defined (WITH_DOUBLE32) + { OPT_LEVELS_ALL, OPT_mdouble_, NULL, 32 }, +#else +#error "align this with config.gcc" +#endif + +#if defined (WITH_LONG_DOUBLE64) + { OPT_LEVELS_ALL, OPT_mlong_double_, NULL, 64 }, +#elif defined (WITH_LONG_DOUBLE32) + { OPT_LEVELS_ALL, OPT_mlong_double_, NULL, 32 }, +#else +#error "align this with config.gcc" +#endif + { OPT_LEVELS_NONE, 0, NULL, 0 } }; + +/* Implement `TARGET_HANDLE_OPTION'. */ + +static bool +avr_handle_option (struct gcc_options *opts, struct gcc_options*, + const struct cl_decoded_option *decoded, location_t loc) +{ + int value = decoded->value; + + switch (decoded->opt_index) + { + case OPT_mdouble_: + if (value == 64) + { +#if !defined (HAVE_DOUBLE64) + error_at (loc, "option %<-mdouble=64%> is only available if " + "configured %<--with-double={64|64,32|32,64}%>"); +#endif + opts->x_avr_long_double = 64; + } + else if (value == 32) + { +#if !defined (HAVE_DOUBLE32) + error_at (loc, "option %<-mdouble=32%> is only available if " + "configured %<--with-double={|32|32,64|64,32}%>"); +#endif + } + else + gcc_unreachable(); + +#if defined (HAVE_LONG_DOUBLE_IS_DOUBLE) + opts->x_avr_long_double = value; +#endif + break; // -mdouble= + + case OPT_mlong_double_: + if (value == 64) + { +#if !defined (HAVE_LONG_DOUBLE64) + error_at (loc, "option %<-mlong-double=64%> is only available if " + "configured %<--with-long-double={64|64,32|32,64}%>, " + "or %<--with-long-double=double%> together with " + "%<--with-double={64|64,32|32,64}%>"); +#endif + } + else if (value == 32) + { +#if !defined (HAVE_LONG_DOUBLE32) + error_at (loc, "option %<-mlong-double=32%> is only available if " + "configured %<--with-long-double={|32|32,64|64,32}%>, " + "or %<--with-long-double=double%> together with " + "%<--with-double={|32|32,64|64,32}%>"); +#endif + opts->x_avr_double = 32; + } + else + gcc_unreachable(); + +#if defined (HAVE_LONG_DOUBLE_IS_DOUBLE) + opts->x_avr_double = value; +#endif + break; // -mlong-double= + } + + return true; +} + + +#undef TARGET_HANDLE_OPTION +#define TARGET_HANDLE_OPTION avr_handle_option + #undef TARGET_OPTION_OPTIMIZATION_TABLE #define TARGET_OPTION_OPTIMIZATION_TABLE avr_option_optimization_table Index: gcc/config/avr/avr-c.c =================================================================== --- gcc/config/avr/avr-c.c (revision 277236) +++ gcc/config/avr/avr-c.c (working copy) @@ -390,6 +390,55 @@ start address. This macro shall be used cpp_define (pfile, "__WITH_AVRLIBC__"); #endif /* WITH_AVRLIBC */ + // From configure --with-double={|32|32,64|64,32|64} + +#ifdef HAVE_DOUBLE_MULTILIB + cpp_define (pfile, "__HAVE_DOUBLE_MULTILIB__"); +#endif + +#ifdef HAVE_DOUBLE64 + cpp_define (pfile, "__HAVE_DOUBLE64__"); +#endif + +#ifdef HAVE_DOUBLE32 + cpp_define (pfile, "__HAVE_DOUBLE32__"); +#endif + +#if defined (WITH_DOUBLE64) + cpp_define (pfile, "__DEFAULT_DOUBLE__=64"); +#elif defined (WITH_DOUBLE32) + cpp_define (pfile, "__DEFAULT_DOUBLE__=32"); +#else +#error "align this with config.gcc" +#endif + + // From configure --with-long-double={|32|32,64|64,32|64|double} + +#ifdef HAVE_LONG_DOUBLE_MULTILIB + cpp_define (pfile, "__HAVE_LONG_DOUBLE_MULTILIB__"); +#endif + +#ifdef HAVE_LONG_DOUBLE64 + cpp_define (pfile, "__HAVE_LONG_DOUBLE64__"); +#endif + +#ifdef HAVE_LONG_DOUBLE32 + cpp_define (pfile, "__HAVE_LONG_DOUBLE32__"); +#endif + +#ifdef HAVE_LONG_DOUBLE_IS_DOUBLE + cpp_define (pfile, "__HAVE_LONG_DOUBLE_IS_DOUBLE__"); +#endif + +#if defined (WITH_LONG_DOUBLE64) + cpp_define (pfile, "__DEFAULT_LONG_DOUBLE__=64"); +#elif defined (WITH_LONG_DOUBLE32) + cpp_define (pfile, "__DEFAULT_LONG_DOUBLE__=32"); +#else +#error "align this with config.gcc" +#endif + + /* Define builtin macros so that the user can easily query whether non-generic address spaces (and which) are supported or not. This is only supported for C. For C++, a language extension is needed Index: gcc/config/avr/avr.c =================================================================== --- gcc/config/avr/avr.c (revision 277236) +++ gcc/config/avr/avr.c (working copy) @@ -768,6 +768,9 @@ avr_option_override (void) if (!avr_set_core_architecture()) return; + /* Sould be set by avr-common.c */ + gcc_assert (avr_long_double >= avr_double); + /* RAM addresses of some SFRs common to all devices in respective arch. */ /* SREG: Status Register containing flags like I (global IRQ) */ Index: gcc/config/avr/avr.h =================================================================== --- gcc/config/avr/avr.h (revision 277236) +++ gcc/config/avr/avr.h (working copy) @@ -140,8 +140,9 @@ These two properties are reflected by bu #define LONG_TYPE_SIZE (INT_TYPE_SIZE == 8 ? 16 : 32) #define LONG_LONG_TYPE_SIZE (INT_TYPE_SIZE == 8 ? 32 : 64) #define FLOAT_TYPE_SIZE 32 -#define DOUBLE_TYPE_SIZE 32 -#define LONG_DOUBLE_TYPE_SIZE 32 +#define DOUBLE_TYPE_SIZE (avr_double) +#define LONG_DOUBLE_TYPE_SIZE (avr_long_double) + #define LONG_LONG_ACCUM_TYPE_SIZE 64 #define DEFAULT_SIGNED_CHAR 1 @@ -507,8 +508,10 @@ typedef struct avr_args (LENGTH = avr_adjust_insn_length (INSN, LENGTH)) extern const char *avr_devicespecs_file (int, const char**); +extern const char *avr_double_lib (int, const char**); -#define EXTRA_SPEC_FUNCTIONS \ +#define EXTRA_SPEC_FUNCTIONS \ + { "double-lib", avr_double_lib }, \ { "device-specs-file", avr_devicespecs_file }, /* Driver self specs has lmited functionality w.r.t. '%s' for dynamic specs. @@ -516,7 +519,8 @@ extern const char *avr_devicespecs_file is used to diagnose problems with reading the specs file. */ #undef DRIVER_SELF_SPECS -#define DRIVER_SELF_SPECS \ +#define DRIVER_SELF_SPECS \ + " %:double-lib(%{m*:m%*})" \ " %:device-specs-file(device-specs%s %{mmcu=*:%*})" /* No libstdc++ for now. Empty string doesn't work. */ Index: gcc/config/avr/avr.opt =================================================================== --- gcc/config/avr/avr.opt (revision 277236) +++ gcc/config/avr/avr.opt (working copy) @@ -115,6 +115,24 @@ mabsdata Target Report Mask(ABSDATA) Assume that all data in static storage can be accessed by LDS / STS. This option is only useful for reduced Tiny devices. +mdouble= +Target Report Joined RejectNegative Var(avr_double) Init(0) Enum(avr_bits_e) +mdouble= Use bits wide double type. + +mlong-double= +Target Report Joined RejectNegative Var(avr_long_double) Init(0) Enum(avr_bits_e) +mlong-double= Use bits wide long double type. + nodevicelib Driver Target Report RejectNegative Do not link against the device-specific library lib.a. + +Enum +Name(avr_bits_e) Type(int) +Available BITS selections: + +EnumValue +Enum(avr_bits_e) String(32) Value(32) + +EnumValue +Enum(avr_bits_e) String(64) Value(64) Index: gcc/config/avr/driver-avr.c =================================================================== --- gcc/config/avr/driver-avr.c (revision 277236) +++ gcc/config/avr/driver-avr.c (working copy) @@ -111,3 +111,60 @@ avr_devicespecs_file (int argc, const ch #endif NULL); } + + +/* Re-build the -mdouble= and -mlong-double= options. This is needed + because multilib selection is based on the physical presence of an + option on the command line, which is not the case for, say, when the + double=64 multilib is to be selected by --with-double=64 but the user + does not specify -mdouble=64 explicitly. */ + +const char* +avr_double_lib (int argc, const char **argv) +{ +#if defined (WITH_DOUBLE64) + int dbl = 64; +#elif defined (WITH_DOUBLE32) + int dbl = 32; +#else +#error "align this with config.gcc" +#endif + +#if defined (WITH_LONG_DOUBLE64) + int ldb = 64; +#elif defined (WITH_LONG_DOUBLE32) + int ldb = 32; +#else +#error "align this with config.gcc" +#endif + + for (int i = 0; i < argc; i++) + { + if (strcmp (argv[i], "mdouble=32") == 0) + { + dbl = 32; +#ifdef HAVE_LONG_DOUBLE_IS_DOUBLE + ldb = dbl; +#endif + } + else if (strcmp (argv[i], "mdouble=64") == 0) + { + ldb = dbl = 64; + } + else if (strcmp (argv[i], "mlong-double=32") == 0) + { + ldb = dbl = 32; + } + else if (strcmp (argv[i], "mlong-double=64") == 0) + { + ldb = 64; +#ifdef HAVE_LONG_DOUBLE_IS_DOUBLE + dbl = ldb; +#endif + } + } + + return concat (" % MULTILIB_OPTIONS # m_dirnames <-> MULTILIB_DIRNAMES # m_required <-> MULTILIB_REQUIRED + # m_reuse <-> MULTILIB_REUSE m_sep = "" m_options = "\nMULTILIB_OPTIONS = " m_dirnames = "\nMULTILIB_DIRNAMES =" m_required = "\nMULTILIB_REQUIRED =" + m_reuse = "\nMULTILIB_REUSE =" + + have_double_multi = (HAVE_DOUBLE_MULTILIB == "HAVE_DOUBLE_MULTILIB") + have_long_double_multi = (HAVE_LONG_DOUBLE_MULTILIB == "HAVE_LONG_DOUBLE_MULTILIB") } ################################################################## @@ -130,7 +141,26 @@ BEGIN { # leading "mmcu=avr2/" in order not to confuse genmultilib. gsub (/^mmcu=avr2\//, "", opts) if (opts != "mmcu=avr2") + { m_required = m_required " \\\n\t" opts + if (have_double_multi && have_long_double_multi) + { + m_required = m_required " \\\n\t" opts "/" opt_double64 + m_required = m_required " \\\n\t" opts "/" opt_long_double64 + + # -mlong-double=64 -mdouble=64 is the same as -mdouble=64, + # hence add a respective reuse. + d_opts = opts "/" opt_double64 + d_reuse = opts "/" opt_double64 "/" opt_long_double64 + gsub (/=/, ".", d_opts) + gsub (/=/, ".", d_reuse) + m_reuse = m_reuse " \\\n\t" d_opts "=" d_reuse + } + else if (have_double_multi) + m_required = m_required " \\\n\t" opts "/" opt_double64 + else if (have_long_double_multi) + m_required = m_required " \\\n\t" opts "/" opt_long_double64 + } } } @@ -143,9 +173,37 @@ END { # Output that Stuff ############################################################ - # Intended Target: ./gcc/config/avr/t-multilib + # Intended Target: $(top_builddir)/gcc/t-multilib-avr + + if (have_double_multi && have_long_double_multi) + { + print m_options " " opt_tiny " " opt_rcall " " opt_double64 "/" opt_long_double64 + print m_dirnames " " dir_tiny " " dir_rcall " " dir_double64 " " dir_long_double64 + # Notice that the ./double64 and ./long-double64 variants cannot + # be copied by t-avrlibc because the . default multilib is built + # after all the others. + m_required = m_required " \\\n\t" opt_double64 + m_required = m_required " \\\n\t" opt_long_double64 + m_reuse = m_reuse " \\\n\tmdouble.64=mdouble.64/mlong-double.64" + } + else if (have_double_multi) + { + print m_options " " opt_tiny " " opt_rcall " " opt_double64 + print m_dirnames " " dir_tiny " " dir_rcall " " dir_double64 + m_required = m_required " \\\n\t" opt_double64 + } + else if (have_long_double_multi) + { + print m_options " " opt_tiny " " opt_rcall " " opt_long_double64 + print m_dirnames " " dir_tiny " " dir_rcall " " dir_long_double64 + m_required = m_required " \\\n\t" opt_long_double64 + } + else + { + print m_options " " opt_tiny " " opt_rcall + print m_dirnames " " dir_tiny " " dir_rcall + } - print m_options " " opt_tiny " " opt_rcall - print m_dirnames " " dir_tiny " " dir_rcall print m_required + print m_reuse } Index: gcc/config/avr/t-avr =================================================================== --- gcc/config/avr/t-avr (revision 277236) +++ gcc/config/avr/t-avr (working copy) @@ -16,6 +16,9 @@ # along with GCC; see the file COPYING3. If not see # . +HAVE_DOUBLE_MULTILIB = $(findstring HAVE_DOUBLE_MULTILIB, $(tm_defines)) +HAVE_LONG_DOUBLE_MULTILIB = $(findstring HAVE_LONG_DOUBLE_MULTILIB, $(tm_defines)) + PASSES_EXTRA += $(srcdir)/config/avr/avr-passes.def driver-avr.o: $(srcdir)/config/avr/driver-avr.c \ @@ -93,9 +96,14 @@ install-device-specs: s-device-specs ins # MULTILIB_OPTIONS # MULTILIB_DIRNAMES # MULTILIB_REQUIRED +# MULTILIB_REUSE -s-mlib: $(srcdir)/config/avr/t-multilib +multilib.h Makefile s-mlib: t-multilib-avr -$(srcdir)/config/avr/t-multilib: $(srcdir)/config/avr/genmultilib.awk \ +t-multilib-avr: $(srcdir)/config/avr/genmultilib.awk \ $(AVR_MCUS) - $(AWK) -f $< $< $(AVR_MCUS) > $@ + $(AWK) -v HAVE_DOUBLE_MULTILIB=$(HAVE_DOUBLE_MULTILIB) \ + -v HAVE_LONG_DOUBLE_MULTILIB=$(HAVE_LONG_DOUBLE_MULTILIB) \ + -f $< $< $(AVR_MCUS) > $@ + +include t-multilib-avr Index: gcc/config/avr/t-multilib =================================================================== --- gcc/config/avr/t-multilib (revision 277236) +++ gcc/config/avr/t-multilib (nonexistent) @@ -1,46 +0,0 @@ -# Auto-generated Makefile Snip -# Generated by : ./gcc/config/avr/genmultilib.awk -# Generated from : ./gcc/config/avr/avr-mcus.def -# Used by : tmake_file from Makefile and genmultilib - -# Copyright (C) 2011-2019 Free Software Foundation, Inc. -# -# This file is part of GCC. -# -# GCC 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, or (at your option) any later -# version. -# -# GCC 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 GCC; see the file COPYING3. If not see -# . - -MULTILIB_OPTIONS = mmcu=avr2/mmcu=avr25/mmcu=avr3/mmcu=avr31/mmcu=avr35/mmcu=avr4/mmcu=avr5/mmcu=avr51/mmcu=avr6/mmcu=avrxmega2/mmcu=avrxmega3/mmcu=avrxmega4/mmcu=avrxmega5/mmcu=avrxmega6/mmcu=avrxmega7/mmcu=avrtiny msp8 mshort-calls - -MULTILIB_DIRNAMES = avr2 avr25 avr3 avr31 avr35 avr4 avr5 avr51 avr6 avrxmega2 avrxmega3 avrxmega4 avrxmega5 avrxmega6 avrxmega7 avrtiny tiny-stack short-calls - -MULTILIB_REQUIRED = \ - msp8 \ - mmcu=avr25 \ - mmcu=avr25/msp8 \ - mmcu=avr3 \ - mmcu=avr31 \ - mmcu=avr35 \ - mmcu=avr4 \ - mmcu=avr5 \ - mmcu=avr51 \ - mmcu=avr6 \ - mmcu=avrxmega2 \ - mmcu=avrxmega3/mshort-calls \ - mmcu=avrxmega3 \ - mmcu=avrxmega4 \ - mmcu=avrxmega5 \ - mmcu=avrxmega6 \ - mmcu=avrxmega7 \ - mmcu=avrtiny Index: gcc/config.gcc =================================================================== --- gcc/config.gcc (revision 277236) +++ gcc/config.gcc (working copy) @@ -1287,6 +1287,88 @@ avr-*-*) tm_file="${tm_file} ${cpu_type}/avrlibc.h" tm_defines="${tm_defines} WITH_AVRLIBC" fi + case y${with_double} in + y | y32) + avr_double=32 + tm_defines="${tm_defines} HAVE_DOUBLE32" + ;; + y64) + avr_double=64 + tm_defines="${tm_defines} HAVE_DOUBLE64" + ;; + y64,32) + avr_double=64 + avr_double_multilib=1 + tm_defines="${tm_defines} HAVE_DOUBLE32" + tm_defines="${tm_defines} HAVE_DOUBLE64" + tm_defines="${tm_defines} HAVE_DOUBLE_MULTILIB" + ;; + y32,64) + avr_double=32 + avr_double_multilib=1 + tm_defines="${tm_defines} HAVE_DOUBLE32" + tm_defines="${tm_defines} HAVE_DOUBLE64" + tm_defines="${tm_defines} HAVE_DOUBLE_MULTILIB" + ;; + *) + echo "Error: --with-double= can only be used with: '32', '32,64', '64,32', '64'" 1>&2 + exit 1 + ;; + esac + case y${with_long_double} in + y | y32) + avr_long_double=32 + tm_defines="${tm_defines} HAVE_LONG_DOUBLE32" + ;; + y64) + avr_long_double=64 + tm_defines="${tm_defines} HAVE_LONG_DOUBLE64" + ;; + y64,32) + avr_long_double=64 + avr_long_double_multilib=1 + tm_defines="${tm_defines} HAVE_LONG_DOUBLE32" + tm_defines="${tm_defines} HAVE_LONG_DOUBLE64" + tm_defines="${tm_defines} HAVE_LONG_DOUBLE_MULTILIB" + ;; + y32,64) + avr_long_double=32 + avr_long_double_multilib=1 + tm_defines="${tm_defines} HAVE_LONG_DOUBLE32" + tm_defines="${tm_defines} HAVE_LONG_DOUBLE64" + tm_defines="${tm_defines} HAVE_LONG_DOUBLE_MULTILIB" + ;; + ydouble) + avr_long_double=${avr_double} + tm_defines="${tm_defines} HAVE_LONG_DOUBLE_IS_DOUBLE" + if test y${avr_double_multilib} = y1; then + tm_defines="${tm_defines} HAVE_LONG_DOUBLE32" + tm_defines="${tm_defines} HAVE_LONG_DOUBLE64" + else + tm_defines="${tm_defines} HAVE_LONG_DOUBLE${avr_long_double}" + fi + ;; + *) + echo "Error: --with-long_double= can only be used with: '32', '32,64', '64,32', '64', 'double'" 1>&2 + exit 1 + ;; + esac + if test ${avr_long_double}x${avr_long_double_multilib}y${avr_double_multilib}z = 32xy1z; then + if test y${with_long_double} != ydouble; then + echo "Error: --with-double=${with_double} requests a multilib for double, but long double is always 32 bits wide due to --with-long-double=${with_long_double}" 1>&2 + exit 1 + fi + fi + if test ${avr_double}x${avr_long_double_multilib}y${avr_double_multilib}z = 64x1yz; then + echo "Error: --with-long-double=${with_long_double} requests a multilib for long double, but double is always 64 bits wide due to --with-double=64" 1>&2 + exit 1 + fi + if test y${avr_double}${avr_long_double} = y6432; then + echo "Error: double default of 64 bits from --with-double=${with_double} conflicts with default of 32 bits for long double from --with-long-double=${with_long_double}" 1>&2 + exit 1 + fi + tm_defines="${tm_defines} WITH_DOUBLE${avr_double}" + tm_defines="${tm_defines} WITH_LONG_DOUBLE${avr_long_double}" tmake_file="${tmake_file} avr/t-avr avr/t-multilib" use_gcc_stdint=wrap extra_gcc_objs="driver-avr.o avr-devices.o" Index: gcc/doc/invoke.texi =================================================================== --- gcc/doc/invoke.texi (revision 277236) +++ gcc/doc/invoke.texi (working copy) @@ -721,6 +721,7 @@ -imacros @var{file} -imultilib @var{dir @gccoptlist{-mmcu=@var{mcu} -mabsdata -maccumulate-args @gol -mbranch-cost=@var{cost} @gol -mcall-prologues -mgas-isr-prologues -mint8 @gol +-mdouble=@var{bits} -mlong-double=@var{bits} @gol -mn_flash=@var{size} -mno-interrupts @gol -mmain-is-OS_task -mrelax -mrmw -mstrict-X -mtiny-stack @gol -mfract-convert-truncate @gol @@ -18226,6 +18227,22 @@ integers. The default branch cost is 0. Functions prologues/epilogues are expanded as calls to appropriate subroutines. Code size is smaller. +@item -mdouble=@var{bits} +@opindex mdouble +Set the size (in bits) of the @code{double} type. Valid values for +@var{bits} are 32 and 64. This option is only available if the compiler +is configured with @code{--with-double=32} or with @code{--with-double=64}, +and the argument of @code{--with-double=} specifies the default layout of +@code{double}. + +@item -mlong-double=@var{bits} +@opindex mlong-double +Set the size (in bits) of the @code{long double} type. Valid values for +@var{bits} are 32 and 64. This option is only available if the compiler +is configured with @code{--with-long-double=32} or with +@code{--with-long-double=64}, and the argument of @code{--with-long-double=} +specifies the default layout of @code{long double}. + @item -mgas-isr-prologues @opindex mgas-isr-prologues Interrupt service routines (ISRs) may use the @code{__gcc_isr} pseudo Index: libgcc/config/avr/t-avr =================================================================== --- libgcc/config/avr/t-avr (revision 277236) +++ libgcc/config/avr/t-avr (working copy) @@ -112,10 +112,14 @@ LIB2FUNCS_EXCLUDE = \ _clrsbdi2 \ -# We do not have the DF type. +ifeq ($(long_double_type_size),32) +# We do not have the DFtype. +HOST_LIBGCC2_CFLAGS += -DDF=SF +endif + # Most of the C functions in libgcc2 use almost all registers, # so use -mcall-prologues for smaller code size. -HOST_LIBGCC2_CFLAGS += -DDF=SF -Dinhibit_libc -mcall-prologues -Os +HOST_LIBGCC2_CFLAGS += -Dinhibit_libc -mcall-prologues -Os # Extra 16-bit integer functions. intfuncs16 = _absvXX2 _addvXX3 _subvXX3 _mulvXX3 _negvXX2 _clrsbXX2 Index: libgcc/config/avr/t-avrlibc =================================================================== --- libgcc/config/avr/t-avrlibc (revision 277236) +++ libgcc/config/avr/t-avrlibc (working copy) @@ -64,3 +64,34 @@ LIB2FUNCS_EXCLUDE += \ _fixunssfsi _fixsfdi \ _fixunssfdi \ _floatdisf _floatundisf + +ifneq (,$(findstring avr,$(MULTISUBDIR))) + +# We are not in the avr2 (default) subdir, hence copying will work. +# In default dir, copying won't work because the default multilib is +# built after all the others. + +ifneq (,$(findstring double64,$(MULTISUBDIR))) + +# We are in double64/libgcc or long-double64/libgcc: +# Just copy from the [long ]double=float multilib; we would remove any DFmode +# bits from this multilib variant, anyway, because the current assumption +# is that avr-libc hosts *all* the IEEE-double stuff. + +LIB2FUNCS_EXCLUDE := % +LIB1ASMFUNCS := +libgcc-objects := +libgcov-objects := +objects := + +t-copy-libgcc.dep: $(srcdir)/config/avr/t-copy-libgcc + -rm -f libgcc.a + -rm -f libgcov.a + cp $< $@ + +libgcc.a libgcov.a libgcc_tm.h: t-copy-libgcc.dep + +Makefile: t-copy-libgcc.dep + +endif +endif Index: libgcc/config/avr/t-copy-libgcc =================================================================== --- libgcc/config/avr/t-copy-libgcc (nonexistent) +++ libgcc/config/avr/t-copy-libgcc (working copy) @@ -0,0 +1,13 @@ +# Only used with --with-avrlibc & (-mlong-double=64 | -mdouble=64) +# +# Inserted at the end of Makefile by magic[tm]. +# We need this *after* Makefile's rules so we can override them. + +libgcc.a: ../../libgcc/libgcc.a + cp $< $@ + +libgcov.a: ../../libgcc/libgcov.a + @: +ifeq ($(enable_gcov),yes) + cp $< $@ +endif