为什么这个Ada程序不抛出约束错误?

为什么这个Ada程序不抛出约束错误?,ada,Ada,我期望下面的代码在编译时抛出一个约束错误,但是它没有。它也不会在c2分配上引发运行时错误。编辑:使用-gnata运行编译器可以解决编译警告问题,但不能解决缺少运行时错误问题。它是使用gnatfsf编译的,没有任何优化,只是:gnatmakemain编辑:gnatmake-gnatamain with Ada.Text_IO; use Ada.Text_IO; procedure Main is subtype cat is Integer with Dynamic_Predicate

我期望下面的代码在编译时抛出一个约束错误,但是它没有。它也不会在c2分配上引发运行时错误。编辑:使用-gnata运行编译器可以解决编译警告问题,但不能解决缺少运行时错误问题。它是使用gnatfsf编译的,没有任何优化,只是:gnatmakemain编辑:gnatmake-gnatamain

with Ada.Text_IO; use Ada.Text_IO;

procedure Main is
    subtype cat is Integer with Dynamic_Predicate => cat in 1 .. 9;

    c1 : cat;
    c2 : cat;
begin
    c1 := 5;
    c2 := 99;
end Main;
我认为动态_谓词行本质上等同于以下内容:

subtype cat is Integer range 1 .. 9;

构建您的示例时,会收到编译时警告和运行时错误:

$ gnatmake -gnata -gnato -fstack-check -gnat12 -gnatyO -gnatv -gnati1 -gnatf -gnatn -m -j0 main.adb
gcc-6 -c -gnata -gnato -fstack-check -gnat12 -gnatyO -gnatv -gnati1 -gnatf -gnatn main.adb

GNAT 6.3.0 20170516
Copyright 1992-2016, Free Software Foundation, Inc.

Compiling: main.adb
Source file time stamp: 2018-08-02 06:08:55
Compiled at: 2018-08-02 08:11:00

    10.     c2 := 99;
                  |
        >>> warning: expression fails predicate check on "cat"

 11 lines: No errors, 1 warning
gnatbind-6 -x main.ali
gnatlink-6 main.ali -fstack-check
$ ./main

raised SYSTEM.ASSERTIONS.ASSERT_FAILURE : Dynamic_Predicate failed at main.adb:10
$ 
我想问您的问题是GCC/GNAT中的默认断言策略是
Ignore
。我使用标志
-gnata
来覆盖它


请注意,编译器只给您一个警告。这是因为该程序是完全合法的,即使它会在运行时引发异常。(这是相同的,无论您使用
范围
静态谓词
动态谓词
来指定子集。)

@PaulCrovella您引用的问题回答了缺少编译错误的问题,但没有说明为什么在实际执行程序时不会产生运行时错误。您可以将谓词设置为静态。该表达式是静态谓词所允许的表达式之一。您使用的是哪个FSF GCC?@SimonWright我使用的是TDM-GCC-64,即GCC版本5.1.0(tdm64-1)。这是通过Windows10Pro上的GitBash终端实现的。