糾結(jié)了兩天,終于重新開(kāi)始寫了,這兩天一直卡在硬件iic上,由于硬件iic是比較難啃的一塊骨頭,問(wèn)題一大堆,明明感覺(jué)配置好,測(cè)試時(shí),一會(huì)出這個(gè)問(wèn)題,一會(huì)出那個(gè)問(wèn)題,哎,說(shuō)多了都是淚。。。。
最后木有辦法了,總不能吊死在一棵樹(shù)上吧,然后就寫了個(gè)模擬的iic的,由于對(duì)iic研究和應(yīng)用的比較多(我們實(shí)驗(yàn)室的設(shè)備都是iic通信的,所有設(shè)備的驅(qū)動(dòng)都是我來(lái)寫的),所以在搞這個(gè)的時(shí)候得心應(yīng)手,一個(gè)小時(shí)就把所有的搞定了,有花了1個(gè)小時(shí)把eeprom(at24c02)調(diào)通;
我大致測(cè)了下,我的板子上的eeprom電路類似這個(gè):
所以我要做的是就是把PB6配置稱時(shí)鐘線SCL,PB7配置成數(shù)據(jù)線SDA
這里我們?cè)倥渲幂敵龅臅r(shí)候,要把管腳配置成 General purpose output push-pull模式,具體原因看datasheet關(guān)于管腳配置的那章口頭,說(shuō)的很清楚;
先給大家看看我的頭文件里面的定義
#ifndef __IIC_H__
#define __IIC_H__
#define INPUT 0x8
#define OUTPUT 0x3
/* Config GPIOx */
#define IIC GPIOB
#define SCL_BIT 6
#define SDA_BIT 7
/*Set & Get GPIOx Value*/
#define SET_SDA(a) do{
if(a) IIC->ODR |= 1< #define SET_SCL(a) do{ if(a) IIC->ODR |= 1< #define SDA_OUT do{ IIC->CRL &= ~((unsigned int)0xf<<(4*SDA_BIT)); IIC->CRL |= (unsigned int)OUTPUT<<(4*SDA_BIT); }while(0) #define SDA_IN do{ IIC->CRL &= ~((unsigned int)0xf<<(4*SDA_BIT)); IIC->CRL |= (unsigned int)INPUT<<(4*SDA_BIT); }while(0) #define SDA_VAL (IIC->IDR&(1< #define SDA_L SET_SDA(0) #define SCL_H SET_SCL(1) #define SCL_L SET_SCL(0) #define DELAY delay_us(10) #define SLAVE_ADDR 0xA0 #define IIC_READ 0x01 #define IIC_WRITE 0x00 extern int iic_init(void); extern void iic_start(void); extern void iic_stop(void); extern void iic_send_ack(unsigned char ack); extern unsigned char iic_recv_ack(void); extern void iic_send(unsigned char bit); extern unsigned char iic_send_byte(unsigned char dat); extern unsigned char iic_recv(void); extern unsigned char iic_recv_byte(void); extern int iic_send_str(char str[],int len); extern void iic_recv_str(char str[],int len); #endif 下面是iic的應(yīng)用函數(shù) #include <stm32f10x.h> #include "init.h" #include "iic.h" /* SCL PB6 SDA PB7 */ int iic_init() { RCC->APB2ENR |= 1<<3; //Set Clock for GPIOB IIC->CRL &= ~((unsigned int)0xf<<(4*SCL_BIT)); IIC->CRL |= (unsigned int)OUTPUT<<(4*SCL_BIT); //config scl IIC->CRL &= ~((unsigned int)0xf<<(4*SDA_BIT)); IIC->CRL |= (unsigned int)OUTPUT<<(4*SDA_BIT); //config sda return 1; } void delay5us() { DELAY; } /* iic start */ void iic_start() { SDA_OUT; SCL_H; SDA_H;DELAY; SDA_L;DELAY; SCL_L; } /* iic stop */ void iic_stop() { SDA_OUT; SCL_L;SDA_L; SCL_H;DELAY; SDA_H;DELAY; } /* * iic send ack * ack (0:ACK 1:NAK) */ void iic_send_ack(unsigned char ack) { SDA_OUT;SCL_L; if(ack == 0x00) SDA_L; if(ack == 0x01) SDA_H; DELAY; SCL_H;DELAY; SCL_L;DELAY; } /* receive ack */ unsigned char iic_recv_ack() { u32 val = 0; SDA_IN; SCL_H;DELAY; val = SDA_VAL; SCL_L;DELAY; return (val!=0 ? 1:0); } /* send one bit*/ void iic_send(unsigned char bit) { SCL_L; if(bit == 0x01) SDA_H; else SDA_L; DELAY; SCL_H;DELAY; SCL_L;DELAY; } /* send one byte */ unsigned char iic_send_byte(unsigned char dat) { unsigned char i = 0; SDA_OUT; for(i=0; i<8; i++) { if(dat & 0x80) iic_send(0x01); else iic_send(0x00); dat <<= 1; } return 1; } /* iic receive bit */ unsigned char iic_recv() { u32 bit = 0; SCL_L; SCL_H;DELAY; bit = SDA_VAL; SCL_L;DELAY; return (bit!=0 ? 1:0); } /* iic receive byte */ unsigned char iic_recv_byte() { unsigned char i; unsigned char dat = 0; SDA_IN; for (i=0; i<8; i++) { dat <<= 1; dat |= iic_recv(); } return dat; } int iic_send_str(char str[],int len) { int i=0; for(i=0; i iic_send_byte(str[i]); if(iic_recv_ack()) return i; } return len; } void iic_recv_str(char str[],int len) { int i=0; for(i=0; i str[i]=iic_recv_byte(); iic_send_ack(0); } str[i] = '
主站蜘蛛池模板:
兰州市|
乐东|
岐山县|
临湘市|
广西|
巩留县|
长沙县|
孟州市|
光泽县|
牡丹江市|
罗田县|
武冈市|
瓮安县|
巴塘县|
文山县|
建宁县|
绵阳市|
扎赉特旗|
吴桥县|
镇雄县|
达拉特旗|
江川县|
东宁县|
平湖市|
青神县|
吉首市|
乐至县|
华蓥市|
株洲县|
石城县|
巫溪县|
揭东县|
铜鼓县|
西宁市|
麻城市|
乌拉特前旗|
垦利县|
始兴县|
晋江市|
田林县|
浪卡子县|