STM32L010でソフトウェアI2Cスレーブで遊ぶ　その1



目的
I2Cスレーブの規格を都合よく解釈して
I2Cスレーブを作ってみた。

フルの移行図なんか完全に無視


イメージです。


![o_con368.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/99807b40-0ca1-c591-9d7d-5d564678dceb.jpeg)




![o_con400.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/b4815b6d-86d2-551e-d42c-b61534d78a82.jpeg)



テストて使ったI2Cマスター (修正前)


https://qiita.com/caa45040/items/6cfdcb4c7319a0456ee4



```c++





//soft_i2c_slave_test_010_1


#include "mbed.h"

//GPIOの初期化
DigitalOut myled(PB_4);//LED1

//シリアルの初期化
//Serial pc(SERIAL_TX, SERIAL_RX); //nucleo 303
RawSerial pc(PA_2, PA_3); //010


DigitalIn  SDA1(PA_10);
DigitalIn  SCL1(PA_9);

int TinmOut1 = 100000;


//SDAがHの間は、ループ
#define SDA_START() while(SDA1 == 1){}



//SDAがHの間は、ループ TinmOut1付き
#define SDA_H() while(SDA1 == 1 && TinmOut1 != 0){TinmOut1--;}

//SDAがLの間は、ループ TinmOut1付き
#define SDA_L() while(SDA1 == 0 && TinmOut1 != 0){TinmOut1--;}

//SCLがHの間は、ループ TinmOut1付き
void SCL_H() {while(SCL1 == 1 && TinmOut1 != 0){TinmOut1--;}}

//SCLがLの間は、ループ TinmOut1付き
void SCL_L() {while(SCL1 == 0 && TinmOut1 != 0){TinmOut1--;}}

int input,input_bk=1;

//立ち上がり
void SCL_UP_H()
{
    while(TinmOut1 != 0){
       
       //立ち上がり
       input = SCL1;
       if( input_bk != input ){
           if( input == 1 ) break;
       }//endif
       
      //バックアップの保存
      input_bk = input;
      
      TinmOut1--; 
    }//while
}//SCL_UP_H()

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

    char buf[10]; //I2Cバッファー
    int ii; //ループカウンター

    //アドレス
    int a0,a1,a2,a3,a4,a5,a6,a7;
    int a[8];

    //データ
    int d0,d1,d2,d3,d4,d5,d6,d7;
    int d[8];



    //無限ループ
    while(1) {


        //スタート信号の立下りを待つ
        //タイムアウトの設定
        TinmOut1=100000;        

        //開始
        SDA_START();
        

        //アドレスの取り込み
        SCL_H();
        SCL_L();
        a7 = SDA1;
        
        SCL_H();
        SCL_L();
        a6 = SDA1;
        
        SCL_H();
        SCL_L();
        a5 = SDA1;
        
        SCL_H();
        SCL_L();
        a4 = SDA1;

        SCL_H();
        SCL_L();
        a3 = SDA1;

        SCL_H();
        SCL_L();
        a2 = SDA1;

        SCL_H();
        SCL_L();
        a1 = SDA1;

        SCL_H();
        SCL_L();
        a0 = SDA1;


        //a7 = 1;
        //a6 = 0;
        //a5 = 0;
        //a4 = 0;
        //a3 = 0;
        //a2 = 0;
        //a1 = 0;
        //a0 = 0;

        //アンクの処理
        SCL_H();
        SCL_L();
        //a0 = SDA1;

        //データの取り込み

        SCL_H();
        SCL_L();
        d7 = SDA1;

        SCL_H();
        SCL_L();
        d6 = SDA1;

        SCL_H();
        SCL_L();
        d5 = SDA1;

        SCL_H();
        SCL_L();
        d4 = SDA1;

        SCL_H();
        SCL_L();
        d3 = SDA1;

        SCL_H();
        SCL_L();
        d2 = SDA1;

        SCL_H();
        SCL_L();
        d1 = SDA1;

        SCL_H();
        SCL_L();
        d0 = SDA1;

        //d7 = 0;
        //d6 = 0;
        //d5 = 1;
        //d4 = 1;
        //d3 = 0;
        //d2 = 0;
        //d1 = 0;
        //d0 = 0;


        myled = 1; //LED ON  debug

        buf[0] = 'U';//バッファーのクリア


        //I2Cスレーブの受信データの表示
        pc.putc(buf[0]);
        pc.printf("\r\n");
        

        //I2Cスレーブの受信データの表示 debug
        //pc.printf("Read A: %x\r\n", buf[0]);

        myled = 0; //LED OFF  debug


        a[7]=a0;
        a[6]=a1;
        a[5]=a2;
        a[4]=a3;
        a[3]=a4;
        a[2]=a5;
        a[1]=a6;
        a[0]=a7;
        
        d[7]=d0;
        d[6]=d1;
        d[5]=d2;
        d[4]=d3;
        d[3]=d4;
        d[2]=d5;
        d[1]=d6;
        d[0]=d7;

        //アドレスの表示
        for(ii=0; ii<8; ii++) {
            if(ii == 4) pc.printf(": ");
            
            if(a[ii] == 0){
                pc.printf("__ ");
            }else {
                pc.printf("[] ");   
            }
        }
        pc.printf("\r\n");


        //データの表示
        for(ii=0; ii<8; ii++) {
             if(ii == 4) pc.printf(": ");
             
             if(d[ii] == 0){
                pc.printf("__ ");
            }else {
                pc.printf("[] ");   
            }
           

        }
        pc.printf("\r\n");

        wait_ms(500);

    }//while

}//main


//容量削減
void error(const char* format, ...){}






```