目次: C言語とlibc
スレッドごとに独立したデータを保持する空間をTLS(Thread Local Storage)といいます。日本語だと「スレッド局所記憶」というそうです。TLSへのアクセス方法、TLSの初期化方法などはアーキテクチャ依存ですので、今回はglibcのRISC-V版の実装を観察します。
変数宣言は __libc_tsd_define() マクロを使います。例として文字処理に使われるctype関連の変数を見ます。
// glibc/ctype/ctype-info.c
__libc_tsd_define (, const uint16_t *, CTYPE_B)
__libc_tsd_define (, const int32_t *, CTYPE_TOLOWER)
__libc_tsd_define (, const int32_t *, CTYPE_TOUPPER)
// glibc/sysdeps/generic/libc-tsd.h
#define __libc_tsd_define(CLASS, TYPE, KEY) \
CLASS __thread TYPE __libc_tsd_##KEY attribute_tls_model_ie;
// glibc/include/libc-symbols.h
#define attribute_tls_model_ie __attribute__ ((tls_model ("initial-exec")))
マクロは下記のように展開されます。
// glibc/ctype/ctype-info.c
__libc_tsd_define (, const uint16_t *, CTYPE_B)
↓
__thread const uint16_t * __libc_tsd_CTYPE_B __attribute__ ((tls_model ("initial-exec")));
// glibc/include/ctype.h
__libc_tsd_define (extern, const uint16_t *, CTYPE_B)
↓
extern __thread const uint16_t * __libc_tsd_CTYPE_B __attribute__ ((tls_model ("initial-exec")));
ごちゃごちゃして見えますが、普通の変数宣言との違いは__thread指定子とtls_model("initial-exec") 属性の2つです。
これだけだと「そうですか」で終わってしまうので、もう少し詳しく調べます。
スレッドローカル変数のモデルは、Common Variable Attributes - Using the GNU Compiler Collection (GCC) を見る限り4種類あるようです。
それぞれの意味は悲しいことにGCCのマニュアルに書いていないのです。どうして……。参考になるマニュアルとしては、-ftls-model (-qtls) - XL C/C++ for Linux - IBM Documentation もしくは スレッド固有ストレージのアクセスモデル - Oracle Solaris 11.1リンカーとライブラリガイドがわかりやすいです。
Solarisのリンカーのモデル名はGCCと少し違いますが、一見して対応がわかる程度の差でしょう。
次回は変数のアドレス取得について見たいと思います。
< | 2022 | > | ||||
<< | < | 04 | > | >> | ||
日 | 月 | 火 | 水 | 木 | 金 | 土 |
- | - | - | - | - | 1 | 2 |
3 | 4 | 5 | 6 | 7 | 8 | 9 |
10 | 11 | 12 | 13 | 14 | 15 | 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 |
24 | 25 | 26 | 27 | 28 | 29 | 30 |
合計:
本日:
管理者: Katsuhiro Suzuki(katsuhiro( a t )katsuster.net)
This is Simple Diary 1.0
Copyright(C) Katsuhiro Suzuki 2006-2023.
Powered by PHP 8.2.15.
using GD bundled (2.1.0 compatible)(png support.)