⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ds18b20读写程序.v

📁 对DS18B20进行实时读取
💻 V
📖 第 1 页 / 共 3 页
字号:
//------------------------------DS18B20-------------------------------------------
//               		DS18B20温度测量实验
//         				 网址:http://www.wejay.com
//       		功能:在数码管上显示当前DS18B20测到的温度
//           	小数部分为1位,温度为负时,最高位显示"-"
//			  	 		DS18B20测量范围:-55℃ ~ +125℃,
//			  	 		本程序所测范围-55℃ ~ +55℃,
//------------------------------------------------------------------------------------
`define	SKIP_ROM 			8'b11001100//command 0xcc
`define CONVERT 			8'b01000100//command 0x44
`define READ_SCRATCHPAD		8'b10111110//command 0xbe

module pro4(rst,clk,data,decode_value,scan_bit);
input rst;						//K3 input
input clk;						//50M clcok input
inout data;						//ds18b20 data pin
output[7:0] decode_value;		//segment output
output[7:0] scan_bit;			//bit scan output
reg[11:0] counter_wr;			//write time sequence counter
reg[11:0] counter_rd;			//read time sequence counter
reg[15:0] counter_rst;			//reset sequence counter
reg[25:0] counter_test;			//convert wait time counter
reg temp_sign;					//'1'negtive temperature,'0' postive temperature
reg[3:0] temp0;					//low temperature BCD num
reg[7:0] temp1;					//high temperature BCD num
reg[3:0] ini_value;				//load the 4 bit num of the temperature
reg[7:0] decode_value;			//segment output num
reg[16:0] scan_counter;			//define the clock of the led scan
reg[3:0] scan_bit;				//bit scan num
reg link_data;					//tri-state control
reg ff;							//task finish flag
reg[7:0]send_reg;				//send buff
reg[12:0] recv_reg;				//recv buff
reg[12:0] recv_reg_copy;		//copy the data of the recv_reg
reg[9:0] wr_state;				//write state
reg[13:0]rd_state;				//read state
reg[8:0] main_state;			//main state
//----------------------------define main state-----------------------------------
parameter		IDLE				=9'b000000001,
				RESET1				=9'b000000010,
				CMDCC				=9'b000000100,
				CMD44				=9'b000001000,
				DELAY				=9'b000010000,
				RESET2				=9'b000100000,
				CMDCC2				=9'b001000000,
				GET_TEMP			=9'b010000000,
				READ_BIT			=9'b100000000;
//----------------------------define write state-----------------------------------


parameter	    WR_IDLE      	  	=9'b000000001,
                WR_BIT0      		=9'b000000010,
                WR_BIT1      		=9'b000000100,
                WR_BIT2      		=9'b000001000,
                WR_BIT3      		=9'b000010000,
                WR_BIT4      		=9'b000100000,
                WR_BIT5     		=9'b001000000,
                WR_BIT6     		=9'b010000000,
                WR_BIT7      		=9'b100000000;

//---------------------------define read state------------------------------------
parameter      	RD_IDLE   			=14'b00000000000001,
                RD_BIT0   			=14'b00000000000010,
                RD_BIT1   			=14'b00000000000100,
                RD_BIT2  			=14'b00000000001000,
                RD_BIT3  			=14'b00000000010000,
                RD_BIT4   			=14'b00000000100000,
                RD_BIT5   			=14'b00000001000000,
                RD_BIT6   			=14'b00000010000000,
                RD_BIT7   			=14'b00000100000000,
                RD_BIT8   			=14'b00001000000000,
                RD_BIT9   			=14'b00010000000000,
 				RD_BIT10   			=14'b00100000000000,
 				RD_BIT11   			=14'b01000000000000,
				RD_BIT12   			=14'b10000000000000;

assign data=(link_data)?1'b0 : 1'bz;
//-------------------------main state machine-------------------------------------
//9 states:IDLE,RESET1,CMDCC,CMD44,DELAY,RESET2,CMDCC2,GET_TEMP,READ_BIT
//----------------------------------------------------------------------------------
always @(posedge clk)
	begin
		if(!rst)                                //rst to initialize the reg and the state
			begin
				link_data<=0;
				main_state<=IDLE;
				wr_state<=WR_IDLE;
				rd_state<=RD_IDLE;
				counter_test<=0;
				counter_wr<=0;
				counter_rd<=0;
				counter_rst<=0;
				ff<=0;
				temp_sign<=0;
				recv_reg<=0;
				send_reg<=0;
			end
		else
			begin
				casex(main_state)
					IDLE:
						begin
							main_state<=RESET1;
						end
					RESET1:					//reset time sequence 490us low 490us tri-state
						begin
							if(ff==0)
								reset;
							else
								begin
									ff<=0;
									send_reg<=`SKIP_ROM;
									main_state<=CMDCC;//load 0xcc command
								end
						end
					CMDCC:					//write 0xcc command
						begin
							if(ff==0)
								shift8_out;
							else
								begin
									ff<=0;
									send_reg<=`CONVERT;//load 0x44 command
									main_state<=CMD44;
								end
						end
					CMD44:					//write 0x44 command
						begin
							if(ff==0)
								shift8_out;
							else
								begin
									ff<=0;
									main_state<=DELAY;
								end
						end
					DELAY:					//wait for 750ms convert time
							begin
								if(ff==0)
									delay;
								else
									begin
										ff<=0;
										main_state<=RESET2;
									end
							end					
		
							
					RESET2:					//second time reset 
						begin
							if(ff==0)
								reset;
							else
								begin
									ff<=0;
									send_reg<=`SKIP_ROM;//load 0xcc command
									main_state<=CMDCC2;
								end
						end
					CMDCC2:					//write 0xcc command				
						begin
							if(ff==0)
								shift8_out;
							else
								begin
									ff<=0;
									send_reg<=`READ_SCRATCHPAD;//load 0xbe command
									main_state<=GET_TEMP;
								end
						end
					GET_TEMP:				// write 0xbe command			
						begin
							if(ff==0)
								shift8_out;
							else
								begin
									ff<=0;
									main_state<=READ_BIT;
								end
						end
					READ_BIT:				//read 13 bits temperature data
						begin
							if(ff==0)
								shift12_in;
							else
								begin
									ff<=0;
									main_state<=RESET1;
								end
						end
					default:
						begin
							link_data<=0;
							main_state<=IDLE;
							wr_state<=WR_IDLE;
							rd_state<=RD_IDLE;
							ff<=0;
						end
				endcase
			end
		end
		
//------------------------------write task------------------------------------------
//write 0 :pull '0' for 60 us then release the one wire bus(whole cycle:70 us)
//write 1 :pull '0' for 6 us then release the one wire bus (whole cycle :70us)
//---------------------------------------------------------------------------------
task shift8_out;
	begin		
		casex(wr_state)
             WR_IDLE:
                 begin
                    link_data<=0;
					counter_wr<=0;
                    wr_state<=WR_BIT0;
                 end
             WR_BIT0:
				begin
                   if(send_reg[0])
                      begin
                         if(counter_wr==3500)
                            begin
								counter_wr<=0;
                                wr_state<=WR_BIT1;
                                send_reg<=send_reg>>1;
                            end
                         else
							begin
								counter_wr<=counter_wr+1'b1;
                                wr_state<=WR_BIT0;
                                if(counter_wr<300)
                                   link_data<=1;
                                else
                                   link_data<=0;
							end
					 end
                   else
                     begin
                       if(counter_wr==3500)
                          begin
                             wr_state<=WR_BIT1;
                             link_data<=0;
                             send_reg<=send_reg>>1;
							 counter_wr<=0;
                          end
                       else
                          begin
							 counter_wr<=counter_wr+1'b1;
                             wr_state<=WR_BIT0;
                             if(counter_wr<3000)
                                link_data<=1;
                             else
                                link_data<=0;
                          end
                    end
              end
              WR_BIT1:
                  begin
                    if(send_reg[0])
                       begin
                         if(counter_wr==3500)
                            begin
                               wr_state<=WR_BIT2;
                               send_reg<=send_reg>>1;
							   counter_wr<=0;
                            end
                         else
							begin
                               wr_state<=WR_BIT1;
							   counter_wr<=counter_wr+1'b1;
                               if(counter_wr<300)
                                  link_data<=1;
                               else
                                  link_data<=0;
							end
					  end
                    else
					   begin
                          if(counter_wr==3500)
                             begin
								counter_wr<=0;
                                wr_state<=WR_BIT2;
                                link_data<=0;
                                send_reg<=send_reg>>1;
                             end
                          else
                             begin
								counter_wr<=counter_wr+1'b1;
                                wr_state<=WR_BIT1;
                                if(counter_wr<3000)
                                   link_data<=1;
                                else
                                   link_data<=0;
                             end
                       end
                 end
                WR_BIT2:
                    begin
                       if(send_reg[0])
                           begin
                              if(counter_wr==3500)
                                 begin
									counter_wr<=0;
                                    wr_state<=WR_BIT3;
                                    send_reg<=send_reg>>1;
                                 end
                              else
								 begin
									counter_wr<=counter_wr+1'b1;
                                    wr_state<=WR_BIT2;
                                    if(counter_wr<300)
                                       link_data<=1;
                                    else
                                       link_data<=0;
                                 end
							end
                       else
                          begin
                             if(counter_wr==3500)
                                begin
									counter_wr<=0;
                                    wr_state<=WR_BIT3;
                                    link_data<=0;
                                    send_reg<=send_reg>>1;
                                end
                             else
                                begin
									counter_wr<=counter_wr+1'b1;
                                    wr_state<=WR_BIT2;
                                    if(counter_wr<3000)
                                       link_data<=1;
                                    else
                                       link_data<=0;
                                end
                           end
                       end
                    WR_BIT3:
                         begin
                            if(send_reg[0])
                                begin
                                    if(counter_wr==3500)
                                       begin
										   counter_wr<=0;
                                           wr_state<=WR_BIT4;
                                           send_reg<=send_reg>>1;
                                       end
                                     else
                                     begin
										counter_wr<=counter_wr+1'b1;
                                        wr_state<=WR_BIT3;
                                        if(counter_wr<300)
                                           link_data<=1;
                                        else
                                           link_data<=0;
                                    end
                               end
                           else
                              begin
                                  if(counter_wr==3500)
                                     begin
										counter_wr<=0;
                                        wr_state<=WR_BIT4;
                                        link_data<=0;
                                        send_reg<=send_reg>>1;
                                     end
                                  else
                                     begin
										counter_wr<=counter_wr+1'b1;
                                        wr_state<=WR_BIT3;
                                        if(counter_wr<3000)
                                          link_data<=1;
                                        else
                                          link_data<=0;
                                     end

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -