Namespaces
Variants

strcpy, strcpy_s

From cppreference.net
< c ‎ | string ‎ | byte
定義先ヘッダ <string.h>
(1)
char * strcpy ( char * dest, const char * src ) ;
(C99まで)
char * strcpy ( char * restrict dest, const char * restrict src ) ;
(C99から)
errno_t strcpy_s ( char * restrict dest, rsize_t destsz, const char * restrict src ) ;
(2) (C11から)
1) src が指すNULL終端バイト文字列を、NULL終端文字を含めて、 dest が指す文字配列の最初の要素にコピーします。
動作は未定義である、もし dest 配列が十分な大きさでない場合。動作は未定義である、もし文字列が重複している場合。動作は未定義である、もし dest が文字配列へのポインタでないか、または src がヌル終端バイト文字列へのポインタでない場合。
2) (1) と同様ですが、以下の点が異なります:宛先配列の残りの部分を未規定の値で上書きする可能性があり、以下のエラーが実行時に検出され、現在設定されている constraint handler 関数を呼び出します:
  • src または dest がnullポインタである場合
  • destsz がゼロまたは RSIZE_MAX より大きい場合
  • destsz strnlen_s ( src, destsz ) 以下である場合(つまり、切り捨てが発生する場合)
  • ソース文字列と宛先文字列の間にオーバーラップが発生する場合
destが指す文字配列のサイズが strnlen_s ( src, destsz ) 未満の場合、動作は未定義である。言い換えれば、 destsz の誤った値はバッファオーバーフローを引き起こす可能性がある。
すべての境界チェック付き関数と同様に、 strcpy_s は、実装によって __STDC_LIB_EXT1__ が定義されており、かつユーザーが <string.h> をインクルードする前に __STDC_WANT_LIB_EXT1__ を整数定数 1 に定義している場合にのみ利用可能であることが保証される。

目次

翻訳の説明: - 「Contents」を「目次」に翻訳しました - その他のテキスト(Parameters、Return value、Notes、Example、References、See also)はC++関連の専門用語として翻訳せず、原文のまま保持しました - HTMLタグ、属性、クラス名、IDなどはすべて変更せず保持しました - 番号部分もそのまま保持しました

パラメータ

dest - 書き込み先の文字配列へのポインタ
src - コピー元のヌル終端バイト文字列へのポインタ
destsz - 書き込む最大文字数(通常は宛先バッファのサイズ)

戻り値

1) dest のコピーを返す
2) 成功時はゼロを返し、エラー時は非ゼロを返します。また、エラー時には dest [ 0 ] にゼロを書き込みます(ただし dest がnullポインタの場合、または destsz がゼロもしくは RSIZE_MAX より大きい場合を除く)。

注記

strcpy_s は効率を改善するために、書き込まれた最後の文字から destsz までの宛先配列を破壊することが許可されています:マルチバイトブロックでコピーした後、nullバイトをチェックする可能性があります。

関数 strcpy_s はBSD関数 strlcpy と類似していますが、以下の点が異なります

  • strlcpy はソース文字列を切り詰めて宛先に収める(これはセキュリティリスクである)
  • strlcpy strcpy_s が実行するすべてのランタイムチェックを実行しない
  • strlcpy は、呼び出しが失敗した場合に宛先を空文字列に設定したりハンドラを呼び出したりすることで、失敗を明示的に示さない

セキュリティリスクの可能性があるため strcpy_s は切り詰めを禁止していますが、境界チェック付きの strncpy_s を使用することで文字列を切り詰めることが可能です。

#define __STDC_WANT_LIB_EXT1__ 1
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(void)
{
    const char* src = "Take the test.";
//  src[0] = 'M' ; // this would be undefined behavior
    char dst[strlen(src) + 1]; // +1 to accommodate for the null terminator
    strcpy(dst, src);
    dst[0] = 'M'; // OK
    printf("src = %s\ndst = %s\n", src, dst);
#ifdef __STDC_LIB_EXT1__
    set_constraint_handler_s(ignore_handler_s);
    int r = strcpy_s(dst, sizeof dst, src);
    printf("dst = \"%s\", r = %d\n", dst, r);
    r = strcpy_s(dst, sizeof dst, "Take even more tests.");
    printf("dst = \"%s\", r = %d\n", dst, r);
#endif
}

出力例:

src = Take the test.
dst = Make the test.
dst = "Take the test.", r = 0
dst = "", r = 22

参考文献

  • C23規格 (ISO/IEC 9899:2024):
  • 7.24.2.3 strcpy関数 (p: TBD)
  • K.3.7.1.3 strcpy_s関数 (p: TBD)
  • C17規格 (ISO/IEC 9899:2018):
  • 7.24.2.3 strcpy関数 (p: 264-265)
  • K.3.7.1.3 strcpy_s関数 (p: 447)
  • C11規格 (ISO/IEC 9899:2011):
  • 7.24.2.3 strcpy関数 (p: 363)
  • K.3.7.1.3 strcpy_s関数 (p: 615-616)
  • C99規格 (ISO/IEC 9899:1999):
  • 7.21.2.3 strcpy関数 (p: 326)
  • C89/C90標準 (ISO/IEC 9899:1990):
  • 4.11.2.3 strcpy関数

関連項目

指定された文字数をある文字列から別の文字列にコピーする
(関数)
あるバッファから別のバッファにコピーする
(関数)
(C95) (C11)
ワイド文字列を別のワイド文字列にコピーする
(関数)
(dynamic memory TR)
文字列のコピーを割り当てる
(関数)