2018/12/27

[c/c++][CERT]ポインタのtypedefとconst

書いているソースコードを見て、セキュリティとかが甘いと言われた・・・。
く、屈辱だが、意識していないので反論どころか、何も言えるものが無い。


このままじゃまずいなー、と思って探していると、こちらのサイトが見つかった。

CERT C コーディングスタンダード
https://www.jpcert.or.jp/sc-rules/

英語版がすらすら読めるならよかったのだが、残念ながら私には無理だったので、日本語訳してあるのが非常にありがたいので、少しずつ読んでいこう。


読むだけだと身につかないので、気になったところだけブログの記事にしていく予定だ。
長いことC言語で書いているけど、自分の中の常識で固まっている可能性が高いので、初心に帰って読んでいこう。


DCL05-C. typedef による型定義ではポインタ型を避ける
https://www.jpcert.or.jp/sc-rules/c-dcl05-c.html


なんでも、ポインタ型をtypedefすると、それにconstしても思ったようなconstにならないらしい。
えー、ほんとかなぁ。

01: #include <stdio.h>
02: #include <string.h>
03: 
04: struct kuma {
05:     int     a;
06:     char    b[5];
07: };
08: 
09: typedef struct kuma kuma_t;
10: typedef struct kuma* kumaptr_t;
11: 
12: 
13: static void func(const kumaptr_t Kuma)
14: {
15:     Kuma->a = 20;
16:     strcpy(Kuma->b, "def");
17: }
18: 
19: 
20: int main(void)
21: {
22:     kuma_t      k;
23:     k.a = 10;
24:     strcpy(k.b, "abc");
25:     func(&k);
26:     printf("k.a=%d\n", k.a);
27:     printf("k.b=%s\n", k.b);
28:     return 0;
29: }

$ gcc -o tst -Wall -W typedeptr.c
$ ./tst
k.a=20
k.b=def


むう、コンパイラがエラーを出さない時点で書き込めるのはわかったのだが、やっぱりショックだ。

static void func(const kuma_t *Kuma)

引数をこうやると、コンパイルの時点で失敗する。
疑って悪かった。


でも、Win32 APIなんかはそういう定義がたくさんあったよなぁ、と思ったら、下の方に説明があった。
constまで付けたポインタ型をtypedefしたものも用意していて、そっちを使うのだ。
そうだ、確かにCがついた型もあった。そういう理由だったのか。

まあ、ポインタ型をtypedefしないようにしておく方が簡単だな。



あ、関数ポインタがあるやん。
私はあれが苦手で、typedefしてからじゃないと仮引数なんかにできないのだ。。

これも下の方に書いてあった。
関数ポインタ型は例外だ、と。
ありがたい。
いや、別に従わなくてもいいのだが、書いてあると安心するじゃないか。

0 件のコメント:

コメントを投稿

コメントありがとうございます。
スパムかもしれない、と私が思ったら、
申し訳ないですが勝手に削除することもあります。

注: コメントを投稿できるのは、このブログのメンバーだけです。