PIC16C74單片機SPI方式讀寫串行EEPROM程序
;PORTCPINDESCRIPTION
;SCKbit3,SDIbit4,SDObit5,CSbit7
;Fosc=10.0MHz,thuseachinstr.cycle=400ns
;***************RamRegisterDefinitions*******************************
rxdataequ25h
addrequ26h
loopsequ27h
;***************BitDefinitions****************************************
;#defineCSPORTC,7;SPIchipselectbitdefinition
;**********************************************************************
;***************25Cxxxcommanddefinitions
;#defineWREN6;writeenablelatch
;#defineWRDI4;resetthewriteenablelatch
;#defineRDSR5;readstatusregister
;#defineWRSR1;writestatusregister
;#defineREAD3;readdatafrommemory
;#defineWRITE2;writedatatomemory
;Bitdefineswithinstatusregister
;#defineWIP0;writeinprogress
;#defineWEL1;writeenablelatch
;#defineBP02;blockprotectionbit
;#defineBP13;blockprotectionbit
;**********************************************************************
;include"p16c74.inc";16C74includefile
;__CONFIG_WDT_OFF_CP_OFF_HS_OSC_PWRTE_ON
;**********************************************************************
page
org0000;ResetVector
clrfPCLATH;ensurePCLATHbit3iscleared
clrfINTCON;ensureallinterruptsaredisabled
gotostart;jumptothebeginningoftheprogram
org004;interruptvector,donothing
isr:gotoisr;donothing,locationjust
;identifiedincode
;***************BEGINMAINPROGRAM*************************************
;
start:bcfSTATUS,5;needtosetbank0
clrfPORTC;initializeportc
bsfCS;makesurecsisset
bsfSTATUS,5;needtosetbank1
movlw0x10;allbitsareoutputsexceptSDI
movwfTRISC;forSPIsetup
bcfSTATUS,RP0;needtosetbank0
movlw0x31;SPImaster,clk/16,ckp=1
movwfSSPCON;SSPENenabled
movlw0x10;***putbeginningaddressinaddr**
movwfaddr;forlateruse
loop
;ThefirstthingwewilldoistheWREN
callwren;callthewriteenableroutine
;Nextwritestatusreg.tocleartheblockprotectbits
callwrsr;callthewritestatusroutine
;Nextdoabusytest
callbusy_test;testWIPbitinstatusregister
;ThendotheWRENbeforewritingtothearray
callwren;callthewriteenablecommand
;Nextwrite0xA5(oranyothervalue)to0x10
bcfCS;setchipselectlinelow
movlwWRITE;WRITEcontrolbyte
calloutput;calltheoutputsubroutine
movlwb'00000000';highaddrbyteisall0's
calloutput;calltheoutputsubroutine
movfaddr,w;lowaddrbyte
calloutput;calltheoutputsubroutine
movlwb'10100101';load0xA5asdatatobesentout
calloutput;calltheoutputsubroutine
bcfSSPCON,CKP;setclockidlelow,mode0,1
bsfCS;setchipselect,beginwritecycle
bsfSSPCON,CKP;setclockidlehigh,mode1,1
callbusy_test
callrdsr;callthereadstatussubroutine
;Now,readlocation0x10handstoreinrxdata.WithPicmastera
;usercanbreak,readthatmemorylocationtoseeifthereadworked
bcfCS;setchipselectlinelow
movlwREAD;READcontrolbyte
calloutput;calltheoutputsubroutine
movlwb'00000000';highaddrbyteisall0's
calloutput;calltheoutputsubroutine
movfaddr,w;getreadytosendnextbyte
calloutput;calltheoutputsubroutine
movlwb'01011010';movedon'tcarebyteof0x5Ainto
calloutput;calltheoutputsubroutine
bsfCS;bringchipselecthighend
;terminatereadcommand
;Whileprogramiscontinuouslylooping,theusermayhalt(ifusingan
;emulator),andlookatthedatainrxdata.Ifitis0xA5,the
;read/writeworked.
callwait;littledelaybetweenSPIsequence
gotoloop;doitalloveragain
;loopcanbeusedtoevaluateSPI
;signalsonoscilloscope
;*********************BEGINSUBROUTINES*******************************
;***DELAYROUTINE-400uS***
;
waitmovlw.200;timingadjustmentvariable
movwfloops;movevariableintoloops
topnop;sitandwait
nop;nooperation
decfszloops,f;loopcomplete?
gototop;no,goagain
return;yes,returnfromsub
;******ThisistheOUTPUTtransmit/receivesubroutine.***************
outputmovwfSSPBUF;placedatainbuffertosend
loop1bsfSTATUS,RP0;specifybank1
btfssSSPSTAT,BF;hasdatabeenreceived(xmitdone)?
gotoloop1;notdoneyet,keeptrying
bcfSTATUS,RP0;specifybank0
movfSSPBUF,W;emptyreceivebuffer
movwfrxdata;putreceivedbyteintorxdata
return;returnfromsubroutine
;*******WriteEnableSubroutine****************************************
wrenbcfCS;setchipselectlinelow
movlwWREN;WRENcontrolbyte
calloutput;Calltheoutputsubroutine
bcfSSPCON,CKP;setclockidlelow,mode0,1
bsfCS;setchipselect,beginwrite
bsfSSPCON,CKP;setclockidlehigh,mode1,1
return;returnfromsubroutine
;*******ReadStatusRegisterSubroutine********************************
rdsrmovlwRDSR;RDSRcontrolbyte
calloutput;Calltheoutputsubroutine
movlwb'00000101';thisbyteisadon'tcarebyte
calloutput;statusregdatawillbeinrxdata
bsfCS;setchipselect
return;returnfromsubroutine
;*******WriteStatusRegisterSubroutine*******************************
wrsrbcfCS;setchipselectlinelow
movlwWRSR;WRSRcontrolbyte
calloutput;Calltheoutputsubroutine
movlwb'00001000';setBP1bitinstatusregister
calloutput;thiswillclearblockprotectbits
bcfSSPCON,CKP;setclockidlelow,mode0,1
bsfCS;setchipselect
bsfSSPCON,CKP;setclockidlehigh,mode1,1
return;returnfromsubroutine
;*******BusyTest-WIPbitinStatusRegister*************************
busy_test
bcfCS;setchipselectlinelow
movlwRDSR;RDSRcontrolbyte
calloutput;Calltheoutputsubroutine
movlwb'00000000';senddummybyte
calloutput;toinitiateclocksequenceforread
bsfCS;else,setchipselecthigh
btfscrxdata,WIP;testWIPbitreadfromstatusregister
gotobusy_test;repeatbusytest
return;returnfromsubroutine
end
評論