10773


yohjpさんのアドバイス通りにやってみましたが、まだエラーが出てしまいます。

[code]

    (Segment fault)
    
[/code]

再度ご指摘くださると助かります。

[code]

    #include <stdio.h>
    #include <string.h>
    
    
    int written(FILE *file,char* de);
    int readn(FILE *file、char* re);
    int keytype(char* deta,char* read);
    
    int main(void)
    {
        char data[30];
        char read[30];
        char* re=read[0];
        FILE *file;
        file = fopen("sy.txt","w+");
        scanf("%s",data);
        char *de=&data[0];
        char *res;
        res=readn(file,re);
        written(file,de);
        keytype(de,res);
    }
    
    int written(FILE *file,char* de){
        char data_written[30];
        strcpy(data_written,de);
        fprintf(file,"%s",data_written);
        fclose(file);
        return 0;
    }
    
    int readn(FILE *file,char* re){
        fgets(re, 20, file);
        return re;
    }
    
    int keytype(char* data,char* read){
        printf("ABEKOBESANYEAH");
        char data_keytype[30] = "b";
        char read_keytype[30] = "a";
        strcpy(data_keytype,data);
        strcpy(read_keytype,read);
        int i,s,t,sized,sizer;
        sized=sizeof(data_keytype);
        sizer=sizeof(read_keytype);
    
        for(i=0;i<sized;i++){
           for(s=0;s<sizer;s++){
              if(data_keytype[i]==read_keytype[s]){
                if(data_keytype[i+1]==read_keytype[s+1] || s+1<sizer ||i+1<sized){
                  printf("%s,%s",read_keytype[s+1],read_keytype[s+1]);
                }
              }
           }
        }
    }
    
[/code]


CC BY-SA 3.0
2015-05-29T13:02:16.193
10768
2015-06-01T14:18:32.810
2015-06-01T12:42:06.610
9527
9527
question
c
strcpy-sse2-unaligned.S: そのようなファイルやディレクトリはありません


私の環境では、readn() でスタックのポインタを返すのをやめたら、segmentation fault は起きなくなりました。

[code]

    char *readn(FILE *file){
        char data_readn[30];
        fgets(data_readn, 20, file);
        char* re_readn = strdup(&data_readn[0]);
        return re_readn;
    }
    
[/code]


CC BY-SA 3.0
2015-05-29T13:52:05.717
10771
2015-05-29T13:52:05.717
5288
10768
answer


`readn()`関数の実装に原因があります。C言語では、 **関数ローカルな通常の変数を指すポインタ値を、関数の外に持ち出してはいけません** 。

>
[code]

>     int readn(FILE *file){
>        char data_readn[30];
>        fgets(data_readn, 20, file);
>        char* re_readn = &data_readn[0];
>        return re_readn;
>     }
>  
[/code]

「関数ローカルな配列`data_readn[30]`を指しているポインタ(`&data_readn[0]`)」を返していますが、`readn()`関数の呼び出しから`main()`関数に戻ってきたとき、既に`data_readn[30]`が配置されていた30byteメモリ領域は無効になっています。

`keytype()`関数内の`strcpy()`では、この無効なメモリ領域を読み出そうとしてSegmentation faultが発生しています。

下記3パターンの修正方法が考えられます。個人的には、3番目のアプローチが最も好ましいと思います。

  1. `readn()`関数で **`static`** `char data_readn[30];`とし、そのポインタ値を返す。
  2. `readn()`関数でメモリ領域を動的確保(`malloc()`や`strdup()`関数)し、そのポインタ値を返す。ただし、後でメモリ解放(`free()`関数)を行わないとメモリリーク。
  3. `readn()`関数内では配列を宣言せず、呼び出し元(`main()`関数)で用意した配列へのポインタ値を渡す。


CC BY-SA 3.0
2015-05-29T14:15:22.023
10773
2015-05-29T14:15:22.023
49
10768
answer


(1) main()

[code]

    char* re=read[0];
    
[/code]

は

[code]

    char* re= &read[0];
    
[/code]

とread[0]のアドレスを代入してください

(2) readn()  
戻り値は char*型になったので

[code]

    char* readn(FILE *file、char* re);
    
[/code]

となります。

(3) keytype()  
int keytype()が何をするfunctionなのかよくわかりませんが

[code]

    sized=sizeof(data_keytype);
    sizer=sizeof(read_keytype);
    
[/code]

この記述ではsized, sizerの値は共に常に30になります。  
※char型配列(要素数30)のsizeof は30なので。  
続くforループ内で予期しない動作になってないでしょうか？

それぞれの文字列の長さを取得したいのであれば

[code]

    sized=strlen(data_keytype);
    sizer=strlen(read_keytype);
    
[/code]

としてください。

forループ内でi,sが29の時 i+1, s+1を添え字とした配列の値を参照してますが配列の領域外を参照します。

keytype()関数はもう一度仕様どおりの(意図した)実装になっているか確認する事をお薦めします。


CC BY-SA 3.0
2015-06-01T13:46:55.303
10852
2015-06-01T14:18:32.810
2015-06-01T14:18:32.810
7343
7343
10768
answer