fd
まず、を使用してファイル記述子の記述子フラグを取得します
int flags = fcntl(fd, F_GETFL);
次に、Linux 固有の/proc/self/fd/
fd
エントリを使用して記述子を再度開きます。
int newfd;
char buffer[32];
if (snprintf(buffer, sizeof buffer, "/proc/self/fd/%d", fd) < sizeof buffer) {
do {
newfd = open(buffer, flags & ~(O_TRUNC | O_EXCL), 0666);
} while (newfd == -1 && errno == EINTR);
if (newfd == -1) {
/* Error: Cannot reopen file. Error in errno. */
}
} else {
/* Error: the path does not fit in the buffer. */
}
再オープンされたファイル記述子は、newfd
.
O_TRUNC
(ファイルを切り詰める) と(存在する場合は失敗する) がフラグに含まれていないことを確認したい可能性が最も高いことに注意してくださいO_EXCL
。これは、正確な元のフラグを使用して再度開くと望ましくない結果が生じる場合を回避するためです。
名前の変更に関して競合状態が発生するため、を使用したくありません。ユーザーは、上記のコードのと の間でターゲット ファイルの名前を変更します。上記はそれを完全に回避します。lstat()
lstat()
open()
Linux 固有になりたくない/dev/fd/
fd
場合は、上記が失敗した場合に同じことを試みるコードを追加します。一部の Unix システム (およびほとんどの Linux ディストリビューション) でサポートされています。