トップページ > dsPIC入門 > dsPICでI2C(4)

I2C マスター側のプログラム

ソースコード

//********************************************************************
//I2Cマスター側プログラム @dsPIC30F4012
//********************************************************************


//********************************************************************
//ヘッダファイル
#include "p30f4012.h"
#include "uart.h"
#include "i2c.h"


//********************************************************************
//コンフィギュレーション
_FOSC(CSW_FSCM_OFF & XT_PLL8);     //10MHzセラロックを使っているのでクロックは80MHz。
_FWDT(WDT_OFF);
_FBORPOR(PBOR_ON & BORV_20 & PWRT_64 & MCLR_EN);
_FGS(CODE_PROT_OFF);


//********************************************************************
//I2Cの設定パラメータ

unsigned int I2Cconfig1 = I2C_ON & I2C_IDLE_CON & I2C_CLK_HLD & I2C_IPMI_DIS & I2C_7BIT_ADD & I2C_SLW_DIS 
                        & I2C_SM_DIS &I2C_GCALL_DIS & I2C_STR_EN & I2C_NACK & I2C_ACK_DIS & I2C_RCV_DIS
                        & I2C_STOP_DIS & I2C_RESTART_DIS;

unsigned int I2Cconfig2 = 180;        //100kbpsのつもり。


//********************************************************************
//関数プロトタイプ宣言
void writeI2C(char address,char data);
unsigned char readI2C(unsigned char address);
void init_uart(void);


//********************************************************************
//メイン関数
int main(void)
{

 unsigned int i;
 
 //===================================================================
 TRISE = 0x00;
 PORTE = 0x00;
 init_uart();
 //===================================================================
 
 //開く 
 OpenI2C(I2Cconfig1,I2Cconfig2);
 IdleI2C();
 
 //マスター側なので、アドレスは適当な値に設定。
 I2CADD = 0x09; 
 
 putsUART1("I2C start as Master\n\r");
 while(BusyUART1());

 //スレーブ側の立ち上がりを待つ。
 for(i=0;i<60000;i++);

 //データ書き込みテスト
 writeI2C(0x08,'a');
 writeI2C(0x08,'b');


 //データ読み込みテスト
 if(readI2C(0x08) == 'c')
 {
  //デバッグ用に、いろいろ出しておきます。
  putsUART1("Receive Succeeded...\n\r");
  while(BusyUART1());
  
  PORTE = 0xff;
  writeI2C(0x08,'@');
 }

 //I2Cを閉じる
 while(I2CCONbits.PEN);
 CloseI2C();
 

 while(1);

}


//********************************************************************
//7bitアドレス指定で1文字送信
void writeI2C(char address,char data)
{

 //スタートコンディション発行
 StartI2C();

 //待機。これ入れないと動作しません・・・
 IdleI2C(); 

 //アドレスデータを1bitだけ上位へシフト。
 address = address << 1;

 //スレーブへ送信する場合は最下位bitが0です。
 address &= 0b11111110;	

 //アドレス送信
 MasterWriteI2C(address);

 //データ送信完了まで待つ。
 while(I2CSTATbits.TBF);
 
 //スレーブ側からアクノリッジが帰ってきていることを確認
 while(I2CSTATbits.ACKSTAT);
  
 //待機。これ入れないと動作しません・・・
 IdleI2C();
 

 //データ送信
 MasterWriteI2C(data);
 
 //データ送信まで待ちます。
 while(I2CSTATbits.TBF);
  
 //スレーブ側からアクノリッジが帰ってきていることを確認
 while(I2CSTATbits.ACKSTAT);
 
 //待機
 IdleI2C();
  
 //通信を一時停止。
 StopI2C();
 IdleI2C();
}



//********************************************************************
unsigned char readI2C(unsigned char address)
{
 //受信データ格納変数
 unsigned char received_data;

 //スタートコンディション発行
 StartI2C();
 
 //待機
 IdleI2C();

 //アドレスデータを1bitだけ上位へシフト。
 address = address << 1;

 //スレーブから受信する場合は最下位bitが1です。
 address |= 0b00000001;	

 //アドレス送信
 MasterWriteI2C(address);

 //データ送信完了まで待つ。
 while(I2CSTATbits.TBF);
 
 //スレーブ側からアクノリッジが帰ってきていることを確認
 while(I2CSTATbits.ACKSTAT);
 
 //待機。これ入れないと動作しません・・・
 IdleI2C();
 
 //データ受信
 received_data = MasterReadI2C();
 IdleI2C();
  
 //データ送信完了を知らせるためにNACKを返します。
 NotAckI2C();
 IdleI2C();
  
 //通信を一時停止。
 StopI2C();

 return received_data;
}


//********************************************************************

void init_uart(void)
{

 unsigned int config1 = UART_EN & UART_IDLE_CON & UART_ALTRX_ALTTX & UART_NO_PAR_8BIT & UART_1STOPBIT
                     & UART_DIS_WAKE & UART_DIS_LOOPBACK & UART_DIS_ABAUD;

 unsigned int config2 = UART_INT_TX_BUF_EMPTY & UART_TX_PIN_NORMAL & UART_TX_ENABLE & UART_INT_RX_CHAR 
                     & UART_ADR_DETECT_DIS & UART_RX_OVERRUN_CLEAR;

 //115200[bps]に設定。
 OpenUART1(config1,config2,10);
}




前へ   次へ