0

定期的に実行しているときにsegfaultを生成するのはなぜですか?cpy関数を呼び出すときにコマンドライン引数を追加するかコメントアウトすると、segfaultの代わりに未定義の動作ですか?私はn知っポインタのsegfaultと未定義の動作

#include <cstdlib> 
#include <iostream> 
#include <cstring> 
using namespace std; 

int *p; 

void fn() { 
    int n[1]; 
    n[0]=99; 
    p = n; 

} 

void cpy(char *v) { 
    char x[8]; 
    strncpy(x,v,8); 
} 

int main(int argc, char** argv) { 
    fn(); 
    cpy(argv[1]); 
    cout << "p[0]:" << p[0]; 
} 

が機能fnのローカルVARですが、私はバッファをオーバーフローか、nはそれがどこから開催されている値を印刷してもらうことargv[1]として何かを入力することができる方法がある/でしたメモリに?

+2

未定義の動作ですか?コマンドライン引数を追加すると、argv [1]に格納されます。 cpy()行をコメントアウトすると、どこにいてもargv [1]が使用されていないので、segfaultの原因になります。 – Matt

+0

しかし、なぜ 'argv [1]'を使用してsegfaultが発生しないのですか?私はスコープ変数の範囲を指している 'p'のインデックスを出力する未定義の動作を意味しました。 – Austin

+0

cmdlineのargを指定しないか、変数argv [1]を使用しないのと同じように待機しますか? – Matt

答えて

2

引数を渡さない場合は、argv[1]==nullptrです。次にcpy(argv[1])cpy(nullptr)であり、cpyはstrncpy(x,nullptr,8)とsegfaultsを呼び出します。

cpyをコメントアウトすると、segfaultはありません。

引数を渡すと、cpyはsegfaultになりません。しかし、別の問題に遭遇する:fnはp=nでしたが、nはスタック上で宣言されていました。つまり、cout<<p[0]のメインに戻ると、pはもはや存在しないオブジェクトnを指しているので、動作は未定義です。

+0

私の混乱の95%を説明してくれてありがとう。上書きされていなければ 'num 'のデータを出力するために入力を操作する方法を知っていますか? – Austin

+0

'num'と言うと、fnで宣言された' n [] 'を意味しますか? fnが戻る前にそれを印刷するか、fnが戻る前に別の場所に保存する必要があります。 – Waxrat

+0

ええ、申し訳ありません 'n []'私は基本的にコードを変更せずに '99'を出力するようにmainを取得しようとしています。 – Austin

関連する問題