PIC18F14K50を使ったDDS-VFOの心臓部であるAD9834小型DDSモジュールが届きました。早速使用開始のための半田付け工作開始です。久々のハードですが、ユニットで信号線類と電源、アナログ、デジタルグランドの配線だけで済みました。超簡単!でしたHi!
イメージ 1
イメージ 2
イメージ 3
イメージ 4





イメージ 5






DDS-VFOのプログラムは、先の参考ブログのCコードを丸ごと打ち込みしました。久々のコードタイピングで、肩が凝りましたが、何とかコンパイルできるまでにはなっています。コンパイラーはXC8ですので、C18コンパイラーとは以下、若干のコードの変更が必要でした。

long eeprom_read_long(unsigned int adr) 中の以下のEEPROMへの読み込みコマンドと書き込みコマンドです。1行だけサンプル記します。
C18コンパイラーの場合
d= (unsigned long)Read_b_eep(EEPROM +adr*4);

XC8コンパイラーの場合
d= (unsigned long)eeprom_read(EEPROM +adr*4);

単純にコマンドがRead_b_eep を eeprom_read に変えるだけでOKでした。
同様にEEPROMの書き込みコマンドも
単純にコマンドがWrite_b_eep を eeprom_writeに変えるだけでOKです。
もう一つ、Busy_eep();はコマンド書き換え時に削除します。
void eeprom_write_long(unsigned int adr ,long data)
{
      unsigned char i; 
  for( i=0 ; i <4 ; i++){
           eeprom_write(EEPROM + adrs*4 + i ,(unsigned char((data >>(i*8)) & 0x000000ff);
    //Busy_eep();     ←はコメントアウト化か削除します
}

もう一つは、割り込み処理です。これはC18コンパイラーより大夫簡単になります。
C18コンパイラーの場合
---------------------------------------------
#pragma interrupt isr
#pragma code isrcode = 0x8
void isr_direct(void)
{
   _asm
   goto isr
   _endasm
}
#pragma code
void isr(void)
{
...
}
---------------------------------------------
XC8コンパイラーの場合 
上記のコードのvoid isr(void)の前の黄色コードを全部削除し 赤のvoid isr(void)を次の白のコードに書き換えるだけでOKとなります。
---------------------------------------------
void interrupt isr(void)
{
...
}
---------------------------------------------
後はLCDライブラリ(lcd.c,lcd.h)のコマンドが異なるため、自分で用意したライブラリのコマンドに合わせて書き換えることが必要になります。
注意したいのは、プログラム上でも lcd_write() というファンクションを使っているため、LCDのライブラリとコマンドがダブル場合があり得ます。この場合は、下記のvoid lcd_write() を書き換えたほうが紛らわしくなくなると思います。
例えば void disp_write() などとすればLCDのライブラリとは全く異なるようになりますので、完全にダブル事はなくなります。Hi!

void lcd_write(){
    INTCONbits.GIE = 0;
    //lcd_gotopos(0,0); ←ここはオリジナルのLCDコマンド
    LCD_posyx(0,0);  ←ここが書き換えた私の用意したライブラリのコマンド
    if(mode){     
        sprintf(tmp,"IF ");
        //lcd_putstr(tmp); ←ここはオリジナルのLCDコマンド
        LCD_str(tmp);  ←ここが書き換えた私の用意したライブラリのコマンド
        long2comma(offset);       
    }else{
        sprintf(tmp,"VFO");
        //cd_putstr(tmp); ←ここはオリジナルのLCDコマンド
        LCD_str(tmp);  ←ここが書き換えた私の用意したライブラリのコマンド
        long2comma(freq);
    }
    sprintf(tmp,"Hz");
    //lcd_putstr(tmp); ←ここはオリジナルのLCDコマンド
    LCD_str(tmp);   ←ここが書き換えた私の用意したライブラリのコマンド
    if(!mode){
        //lcd_gotopos(0,1); ←ここはオリジナルのLCDコマンド
        LCD_posyx(1,0);  ←ここが書き換えた私の用意したライブラリのコマンド
        if(((freq + offset)> 0) && ((freq + offset)< MAX_FREQ))
            sprintf(tmp,"DDS");
        else
            sprintf(tmp,"ERR");
        //lcd_putstr(tmp); ←ここはオリジナルのLCDコマンド
        LCD_str(tmp);  ←ここが書き換えた私の用意したライブラリのコマンド
        long2comma(freq + offset);
        sprintf(tmp,"Hz");
        //lcd_putstr(tmp); ←ここはオリジナルのLCDコマンド
        LCD_str(tmp);  ←ここが書き換えた私の用意したライブラリのコマンド
    }
    INTCONbits.GIE = 1;
}
もう一つ、LCDのライブラリコマンドのxy座標表示が逆です。私のライブラリは(y,x)の座標指定になります。
自分の使うLCDライブラリで確認する必要があります。
実際の書き換え例)
lcd_gotopos(1,0); ←オリジナルは lcd_gotopos(x座標,y座標)
LCD_posyx(0,1);  ←用意したライブラリ LCD_posyx(y座標,x座標)
以上が主な書き換え部分でした。それから、勿論オリジナルのインクルードするLCDライブラリを私の用意したライブラリに書き換えも必要です。Hi!
#include "lcd.h"  →   #include "L_LCD.h"

以上で、コンパイルは問題なく通ります。しかし、コンパイルが通らないエラーが続出することがありました。これでだいぶ私も時間を取られてしまいました。特にインストールしたMPLAB X IDE v3.30の状態でのコンパイルは注意が必要です。コードが問題なくても、必ずエラーが出ます。何かといいますと、XC8のコンパイラの設定が初期状態では、エラーが出るレベルになっていたということです。気づかなければいやになってPICのプログラムはうまく動かないと思い込んでしまう可能性もあり得ます。
かというと、customize でのXC8のコンパイラーOption categoriesの Preprocessing and message のWarning level 初期値では-3 となっているのです。
これを Warning level 0 にする必要があります。
イメージ 7
前置きがながくなってしまいましたが、本題のEEPROMの書き込みです。読み込み書き込みもコードを書き換えてコンパイルもうまく通り実際の動作をEE Data Memoryで確認してみましたが、EEPROM自体への読み書きができてませんでした。ネットで確認しても、EEPROMの書き込みコマンドも問題ないし、XC8のコンパイラーのユーザーズガイドでも特に問題はありません。何で、うまく動作しないのだろうと思っていました。これも、ネットで調べると、同様な例があり、Macでの対応でしたが、方法としてP18系マイコン用のペリフェラルライブラリをインストールするという解決法でした。やってみましたが、XC8がないだの、インストールができない等と、もうお手上げ状態でした。


がそのあとの文面を読み進んでみて、ペリフェラライブラリを使用する設定があるというので一応見てみました。(結果、ライブラリはインストールされていたため、新たにはインストールしなくても良かったようです。)今度はXC8のLinker の設定項目中のPeripheral Library の項目にチェックを入れるということでした。
イメージ 8

結果これだけで、EEPROMの読み書きができるようになりました。本当に全機能が使えるように最初からは、なっていないということです。使いたいものがあれば、その時に設定で使用できるようにするということになります。以上が本当に時間のかかってしまったEEPROM 奮闘記になります。
他、面白いことにライブラリにチェックがなくても、EEPROMへの初期値の設定だけは(下記)プログラム上で、問題なくできるということがありました。
__EEPROM_DATA (0xC0,0xCF,0x6A,0x00,0x20,0xA1,0x07,0x00);
イメージ 6





DDSのプログラム上では、EEPROMからデータを読み込みその周波数とオフセット周波数をAD9834に送るルーチンで出来ているため、書き込みしておいたデータ周波数を読み込む部分で、デバッグをしていました。ペリフェラルライブラリの使用設定がされてない中では、eeprom_readも堂々巡りだったわけです。
あとプログラム上での、周波数の設定カーソルのルーチンなどうまくない感じなので
時間があれば、少し見てみようと思います。
とにかく動くようになるとPICはとても面白いマイコンでもっと何かやりたいと欲が出てくる楽しい趣味だとつくづく思います。貴重な情報を公開してくださっている先人の方々の苦労には感謝する次第です。Hi!
つづく