メモリチップへのカンマ区切りのデータ書き込みについて

お世話になっております。

使用しているMCU:RX113

RSPIで接続された富士通製FRAM(MB85RS512T)へのデータ書き込みについて、ご教示お願いします。

※ バイト単位でのデータの読み書き、ステータスレジスタの読み込み等はできております。

● 実現したいこと。

カンマで区切られた幾つかのデータをテキストで読める形で書き込むこと。

上記の理由・目的:メモリに蓄積されたデータを外部に送信して、読めること。

● 考えてみたコード (抜粋)

unsigned char Memout[] = "";
unsigned char *Memdata[9];

        Memdata[0] = "20170428 11:12" ","; // 日付・時刻       14Byte
        Memdata[1] = " 12" ",";        // 冷凍機 作動電流値     3Byte
        Memdata[2] = "2.7" ",";        // 扉ヒーター 作動電流値   3Byte
        Memdata[3] = "0.8" ",";        // ドレンヒーター 作動電流値 3Byte
        Memdata[4] = "-17.3" ",";       // 庫内温度          5Byte
        Memdata[5] = "12345" ",";       // 電源ON連続時間     5Byte
        Memdata[6] = "11:12" ",";       // 温度異常時時刻      5Byte
        Memdata[7] = " 85.7" ",";        // 温度異常時の温度     5Byte
        Memdata[8] = "5" "\r\n";        // 扉開閉回数        1Byte

/*  データ送信関数への引渡し */

  data_send(Memdata); // メモリへの書き込みデータ送信

 

※ 上に書きましたコードの初期値は、記憶領域を計算するための覚え書き程度のものです。

● 確認したいこと

  0番目から8番目までのデータは、それぞれ決まった長さ(上記のコードのバイト数)で揃えたいが、この場合

   sprintf(Memdata[n], "%4d,", data );   //  <-  第2項の最後に、カンマが入っています。

 

   という記述で問題はおきないものかどうか。? ということです。

 

お手数をおかけして大変恐縮ですが、何卒よろしくおねがいします。

 

  • わわいです
    ちと質問の意図するところがわかりません
    文字列配列のコメントに書いてあるバイト数は1文字づつ少ないです。
    最後には '\0'が入ります。
    また、Memdata[8] の文字数は1ではありえません

    そして、
    >data_send(Memdata); // メモリへの書き込みデータ送信
    では本当にデータ送信ができてるんでしょうか。

    んで、
    >● 確認したいこと
    の意味がわかりません
  • わわい様

    お世話になっております。

    わかりにくい質問で申し訳ありません。

    メモリへの記録イメージを図にしてみました。

    0番目から9番目のデータを一組としてメモリに書き込むのですが、データの区切りとしてカンマ「,」を入れます。

    ご指摘いただきましたとおり、配列では文字列の最後に'\0'(NULL)が入りますので、各要素は1バイトずつ増えるとして、メモリに送るデータは

    【例】

     char *Memdata[9];

     char delimiter = ',';

     sprintf(Memdata[0], "%d %s", data1, delimiter);

     sprintf(Memdata[1],"%d%s", data2, delimiter);

     /* ・・・・・・・・(中略)・・・・・・・・・ */

     sprintf(Memdata[8],"%d%s", data9, delimiter);

     

     senddata(Memdata);

    と、このような記述で問題は発生しないかどうか、ということを確認したいのです。

    おそらく、もっとスマートな記述方法があると思うのですが・・・

    ご教示よろしくお願いします。

     

     

  • 十分な大きさの Memdata[] を定義した上で

    sprintf(Memdata,"%4d%2d%2d %2d:%2d\r\n", year, month, day, hour, minute);
    

    とすれば 年4桁月2桁日2桁 時2桁:分2桁\r\n\0 の文字列が得られます。項目を増やしたければ sprintf() の第2引数を変更し、minute 以降の引数を追加するだけです。

  • Fujita様
    お世話になっております。
    ご回答ありがとうございます。
    なるほど、それによって各項目毎の長さを定め、一組のデータをつくることができますね。
    そうしますと、配列としては今回の「一組のデータ」の最後に付くCRLFの後に1つのNULLがつくわけですね。

    デリミタである「,」(カンマ)は、変数の一つとしておいたほうがよいものでしょうか、それとも第2引数に記述したほうが間違いが発生しないものなのかどうか…

    明示してもあまり意味がないならば、第2引数に記述したほうがよいような気もしますが、いかがでしょうか。

  • > デリミタである「,」(カンマ)は、変数の一つとしておいたほうがよいものでしょうか、それとも第2引数に記述したほうが間違いが発生しないものなのかどうか…

    場合によって変化するものは引数として値を渡し、常に同じものは書式として第2引数に書いた方が良いでしょう。
  • ポインタの配列の必要性が有るんですか。
    文字列の最大長が16バイトとすれば、16x9バイトの配列を作ったらどうですか。
    文字列は長さが違うので、最大長に合わせると使わない領域が出ます。
    そのために文字列の先頭アドレスを入れたポインタの配列を作ります。
    文字列の長さが一定でコンマの位置も変らないなら、他に工夫できると思います。
  • わわいです

    >char *Memdata[9];
    > char delimiter = ',';
    > sprintf(Memdata[0], "%d %s", data1, delimiter);
    > sprintf(Memdata[1],"%d%s", data2, delimiter);

    えーと、、、なにをしようとしてるのかはまだわからんですが、
    上記のようなコードだとまずいのはわかってるでしょうか。
    不正アクセスが発生するか暴走するかしてしまいますが。。
  • わわい様
    おはようございます、お世話になっております。
    ご返信ありがとうございます。
    皆様からのご教示を整理しておりました。

    正直なところ、これまでお恥ずかしながら配列変数とポインタ変数をごちゃごちゃにしておりました。

    > 上記のようなコードだとまずいのはわかってるでしょうか。
    > 不正アクセスが発生するか暴走するかしてしまいますが。。

    ご指摘のとおりですね。リークが発生して暴走します。(汗;)

    現在のところ、Fujita様よりご指導いただきましたとおり、十分な大きさの配列変数を用意することにしております。

    【要点】
      配列<->ポインタ :式の中で変換される
  • わわいです
    まー、これだけだとなんなんで、


    void makeTxData(char* bff,int* data,int datalen)
    {
    int i;
    for(i=0;i<datalen;i++){
    sprintf(bff,"%d,",*data);
    bff+=strlen(bff);
    data++;
    }
    }

    こーゆールーチンを用意しといて、

    int datamenber[]={ 1,2,3,4 };
    char txbff[80]; // 確保サイズは想定される生成サイズより十分大きくしておくこと

    void main(void)
    {
    makeTxData(txbff,datamember,sizeof(datamember)/sizeof(*datamember));
    // これで、txbff には "1,2,3,4," がはいる

    }

    って、こういうことをしたいのかな?
    まー、最後にコンマが入ってしまうとかバッファのサイズチェックもしたいとか、でーたはintだけじゃないわい、
    とかいろいろツッコミはあるとはおもいますが
  • Fujita様
    御回答ありがとうございます。
    お示しくださいました配列で組みたいと思います。

    ただ1点気になることがあります。
    第2引数がかなり長くなるわけですが、ダブルクォーテーションの途中で改行する方法はあるものでしょうか。
    LFを入れればソースとしては読みやすくなるかもしれませんが、制御文字までメモリに書き込んでは困ります。