00001 /* 00002 **************************************************************************** 00003 * 00004 * simulavr - A simulator for the Atmel AVR family of microcontrollers. 00005 * Copyright (C) 2001, 2002, 2003 Klaus Rudolph 00006 * 00007 * This program is free software; you can redistribute it and/or modify 00008 * it under the terms of the GNU General Public License as published by 00009 * the Free Software Foundation; either version 2 of the License, or 00010 * (at your option) any later version. 00011 * 00012 * This program is distributed in the hope that it will be useful, 00013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 * GNU General Public License for more details. 00016 * 00017 * You should have received a copy of the GNU General Public License 00018 * along with this program; if not, write to the Free Software 00019 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 00020 * 00021 **************************************************************************** 00022 * 00023 * $Id$ 00024 */ 00025 00026 #include "hwwado.h" 00027 #include "avrdevice.h" 00028 #include "systemclock.h" 00029 00030 #define WDTOE 0x10 00031 #define WDE 0x08 00032 00033 00034 void HWWado::SetWdtcr(unsigned char val) { 00035 unsigned char oldWDTOE= wdtcr & WDTOE; 00036 unsigned char newWDE= val & WDE; 00037 00038 if ( newWDE != 0) { //enable the wado allways allowed 00039 wdtcr=val; 00040 } else { //unset the wado 00041 if (oldWDTOE !=0) { //WDTOE was set, 00042 wdtcr=val; 00043 } 00044 } 00045 00046 if ( (val & WDTOE ) != 0) { 00047 cntWde=4; 00048 } 00049 00050 } 00051 00052 unsigned int HWWado::CpuCycle() { 00053 if ( cntWde > 0) { 00054 cntWde--; 00055 00056 } 00057 00058 if (cntWde==0) wdtcr&=(0xff-WDTOE); //clear WDTOE after 4 cpu cycles 00059 00060 if ((( wdtcr& WDE )!= 0 ) && (timeOutAt < SystemClock::Instance().GetCurrentTime() )) { 00061 core->Reset(); 00062 } 00063 00064 00065 return 0; 00066 } 00067 00068 HWWado::HWWado(AvrDevice *c): 00069 Hardware(c), 00070 TraceValueRegister(c, "WADO"), 00071 core(c), 00072 wdtcr_reg(this, "WDTCR", 00073 this, &HWWado::GetWdtcr, &HWWado::SetWdtcr) { 00074 core->AddToCycleList(this); 00075 Reset(); 00076 } 00077 00078 void HWWado::Reset() { 00079 timeOutAt=0; 00080 wdtcr=0; 00081 } 00082 00083 00084 void HWWado::Wdr() { 00085 SystemClockOffset currentTime= SystemClock::Instance().GetCurrentTime(); 00086 switch ( wdtcr& 0x7) { 00087 case 0: 00088 timeOutAt= currentTime+ 47000000; //47ms 00089 break; 00090 00091 case 1: 00092 timeOutAt= currentTime+ 94000000; //94ms 00093 break; 00094 00095 case 2: 00096 timeOutAt= currentTime+ 190000000; //190 ms 00097 break; 00098 00099 case 3: 00100 timeOutAt= currentTime+ 380000000; //380 ms 00101 break; 00102 00103 case 4: 00104 timeOutAt= currentTime+ 750000000; //750 ms 00105 break; 00106 00107 case 5: 00108 timeOutAt= currentTime+ 1500000000; //1.5 s 00109 break; 00110 00111 case 6: 00112 timeOutAt= currentTime+ 3000000000ULL; //3 s 00113 break; 00114 00115 case 7: 00116 timeOutAt= currentTime+ 6000000000ULL; //6 s 00117 break; 00118 00119 } 00120 }