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

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 init_uart(void);


//********************************************************************
//メイン関数

int main(void)
{
 //===================================================================
 //デバッグ用LEDのポート設定
 TRISF = 0x06;
 init_uart();
 //===================================================================
 //開く 
 OpenI2C(I2Cconfig1,I2Cconfig2);   
 //待機
 IdleI2C();
 
  //アドレスを設定
 I2CADD=0x08;

 //割り込み許可
 ConfigIntI2C(MI2C_INT_OFF & SI2C_INT_ON & SI2C_INT_PRI_7);
 
 
 putsUART1("I2C start as Slave\n\r");
 while(BusyUART1());
 
 IdleI2C();

 while(1);
}


//********************************************************************
//I2C割り込み

void _ISR _SI2CInterrupt(void)
{
 unsigned char temp;
	
 //割り込みフラグクリア
 IFS0bits.SI2CIF = 0;	
 
 //とりあえず、自分が指定されたらLEDを点灯。。。
 PORTB = 0x01;
 

 //アドレス受信の場合
 if((I2CSTATbits.R_W == 0) && (I2CSTATbits.D_A == 0))
 {
  //デバッグ用	 
  PORTB = 0x02;
 
  //データを読み出して、レジスタの内容をクリアしておきます。
  temp = SlaveReadI2C(); 
 
  IdleI2C();
 
  //受信動作中はクロックが止まっているので、クロック動作を再開させます。 
  I2CCONbits.SCLREL = 1; 
  
  return;
 }


 //データ受信の場合
 else if((I2CSTATbits.R_W == 0) && (I2CSTATbits.D_A == 1))
 {
  //デバッグ用  
  PORTB = 0x04;
  
  //取得データをUARTで送信しておきます。
  WriteUART1(SlaveReadI2C()); 
  while(BusyUART1());
  putsUART1("\n\r");
  while(BusyUART1());


  //クロック動作再開。
  I2CCONbits.SCLREL = 1; 

  return;
 }
 

 //データ送信要求の場合
 //アドレスを指定されてから、即データを返すので・・・
 //スレーブ側が送信する場合はI2CSTATbits.D_Aは1にならない??
 else if((I2CSTATbits.R_W == 1) && (I2CSTATbits.D_A == 0))
 {
  //デバッグ用	 
  PORTB = 0x08;
  
  IdleI2C();
  
  //デバッグ用文字列を返しておきます。
  SlaveWriteI2C('c');
  
  IdleI2C();

  return;
 } 

 return;
}


//********************************************************************
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);
}



前へ   次へ