🥦

C言語で括弧のネストの深さを制限する(-fbracket-depth)

2021/05/30に公開

はじめに

clangのドキュメントを読んでいたら、
以下のような記載を見つけました。

-fbracket-depth=N
Sets the limit for nested parentheses, brackets, and braces to N. The default is 256.

https://clang.llvm.org/docs/UsersManual.html#controlling-implementation-limits

括弧のネストの深さを制御できるようです。
ちょっと試しに使ってみます。

GCCにこのオプションは?

多分、gccには-fbracket-depthというオプションは無いっぽい。
もしかしたら、違う名称で同じ機能のものがあるかも知れません。
(あったら教えて下さい)

使用してみる

以下のようなコードを用意します。

sample.c
#include <stdio.h>

int main(void) {
    for(int i = 0; i < 5; i++) {
        for(int j = 0; j < 5; j++) {
            for(int k = 0; k < 5; k++) {
                printf("hello\n");
            }
        }
    }
    return 0;
}

コンパイルします。エラーはなく実行もできます。

$ clang  sample.c 
$ ./a.out 
hello
<省略>
hello

次に-fbracket-depthオプションを付けてみます。
エラーとなります。

$ clang -fbracket-depth=3 sample.c 
sample.c:6:40: fatal error: bracket nesting level exceeded maximum of 3
            for(int k = 0; k < 5; k++) {
                                       ^
sample.c:6:40: note: use -fbracket-depth=N to increase maximum nesting level
1 error generated.

以下のように括弧を消してみました。

sample.c
#include <stdio.h>

int main(void) {
    for(int i = 0; i < 5; i++)
        for(int j = 0; j < 5; j++)
            for(int k = 0; k < 5; k++)
                printf("hello\n");
    return 0;
}

こうするとコンパイルはとおります。

$ clang -fbracket-depth=3 sample.c 
$ ./a.out 
hello
<省略>
hello

括弧は(の深さも対象のようです。
以下のような無意味なコードで試してみます。

sample.c
#include <stdio.h>

int f(int i){
    return i;
}

int main(void) {
    printf("%d\n",f(f(f(1))));
    return 0;
}
$ clang -fbracket-depth=3 sample.c 
sample.c:8:24: fatal error: bracket nesting level exceeded maximum of 3
    printf("%d\n",f(f(f(1))));
                       ^
sample.c:8:24: note: use -fbracket-depth=N to increase maximum nesting level
1 error generated.

-fbracket-depth=4とするとコンパイルは通ります。

$ clang -fbracket-depth=4 sample.c 
$ ./a.out 

-fbracket-depthオプションはいつからある?

このあたりで、入ったのでしょうか。(2013年頃?)

https://github.com/llvm/llvm-project/commit/b3a145293dc800bb5bfc8031892713227e686e7e

どういう時に使えるか

どういう時につかえるのでしょうね。
「あまり、ネスト深くしないでね」というルールを
ビルド時に判断できるとかでしょうか。

まとめ

ドキュメントを読むと知らないオプションたくさんあるなぁと思いました。

Discussion