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

📄 speridll.cpp

📁 为keil C 软件模拟方式运行编写的一个闪存模块。
💻 CPP
📖 第 1 页 / 共 2 页
字号:
	
}

AGSITIMER Timer;
byte rxbuf[8192],dbgBuf[8192];
CByteArray rxFifo;
int g_scanInterval=30;
int dbgIndex=0;
BOOL noDebug=1;
static void checkRx(DWORD adr,AGSICB_REASON r) 
{
	// Timer function implementation
	try
	{
		if(!comPort.IsOpen())
		{
			Agsi.SetTimer(Timer, 30000);
			return;
		}
		long dataWaiting=min(comPort.BytesWaiting(),8192);
		if(dataWaiting>0)
		{
			comPort.Read(rxbuf,dataWaiting);
			for(int i=0;i<dataWaiting;i++)
				rxFifo.Add(rxbuf[i]);
		}
		if(rxFifo.GetSize()>0)
		{
			DWORD curV,prev;
			Agsi.ReadSFR(0xFEBa,&curV,&prev,0xff00);
			if(curV==0xff00&&noDebug)
			{
				WORD tmp=rxFifo.GetAt(0);
				if(dbgIndex<8192)
					dbgBuf[dbgIndex++]=tmp;
				listenPort1.Write(&tmp,1);
				Agsi.WriteSFR(0xFEBa,tmp,0xffff);
	//		Agsi.WriteVTR(VTREG[1].hVTR,tmp);
				Agsi.WriteSFR(0xf18a,0x80,0x80);
		//		Agsi.ReadSFR(0xF18A,&curV,&prev,0x80);
				rxFifo.RemoveAt(0);
				g_scanInterval-=2;
			}
			else if(g_scanInterval<2000)
				g_scanInterval++;
		}
	}
	catch(CException *e)
	{
		e->ReportError();
	}
	Agsi.SetTimer(Timer, g_scanInterval);
}

DWORD DefineAllWatches(void)
{      // define all Watches
  BOOL ret = TRUE;
	CString tmp;	

	DWORD iSize=2048;
	DWORD end=g_FlashMemBase+iSize-1;
	
	const char *pMyConfiguration = Agsi.GetTargetKey ("FlashMemoryBase"); // retrieves the string
	if(pMyConfiguration)
		sscanf(pMyConfiguration, "%u", &g_FlashMemBase); // convert string into values…	Update();

	pMyConfiguration = Agsi.GetTargetKey ("FlashMemorySize"); // retrieves the string
	if(pMyConfiguration)
		sscanf(pMyConfiguration, "%u", &g_flashMemSize); // convert string into values…	Update();

	const char *pChar=Agsi.GetTargetKey ("scaninterval");
//	if(pChar)g_scanInterval=atoi(pChar);
	pChar=Agsi.GetTargetKey ("commport");
	if(pChar)g_strComm=pChar;

	if(g_flashMemSize>0)
	{
		end=g_FlashMemBase+g_flashMemSize-1;
		tmp.Format("MAP 0x%x ,0x%x READ WRITE EXEC",g_FlashMemBase,end);
		Agsi.ExecuteCommand(tmp);
		char *pBuf=new char[g_flashMemSize+10];
		try
		{
			g_flashDataFile=Agsi.GetTargetKey("flashDataFile");
			CFile dataFile(g_flashDataFile,CFile::typeBinary|CFile::modeRead);
		  dataFile.Read(pBuf,g_flashMemSize);
		  Agsi.WriteMemory(g_FlashMemBase,g_flashMemSize,(byte*)pBuf);
		}
		catch (CFileException* e)
		{
			e->ReportError();
		}
		delete[] pBuf;
//		ret&=Agsi.SetWatchOnVTR(VTREG[2].hVTR,asc0Tx,AGSIWRITE);
	//	ret&=Agsi.SetWatchOnVTR(VTREG[3].hVTR,asc1Tx,AGSIWRITE);
  	ret&=Agsi.SetWatchOnSFR(0xfeb8,asc1Tx,AGSIWRITE);

	Timer = Agsi.CreateTimer(checkRx);
	//	ret &=Agsi.SetWatchOnMemory(g_FlashMemBase, end,FlashRead,AGSIREAD);
	//	ret &=Agsi.SetWatchOnMemory(g_FlashMemBase, end,FlashWrite,AGSIWRITE);
	}
 // Timer = Agsi.CreateTimer(AdcCompleted);
 // if (!Timer) return(FALSE);														 

  return(ret);
}


DWORD DefineAllMenuEntries(void) {  // declare all peripheral-menu entries and dialogs

  if (!Agsi.DefineMenuItem(&PeriMenu)) return(FALSE);

  return(TRUE);
}


DWORD ResetPeripheral(void) {       // reset all SFR's of this peripheral
  BOOL ret = TRUE;
  
  ret &= Agsi.WriteSFR(ADCCON1,  0x20, 0xFF);
  ret &= Agsi.WriteSFR(ADCCON2,  0x00, 0xFF);
  ret &= Agsi.WriteSFR(ADCCON3,  0x00, 0xFF);
  ret &= Agsi.WriteSFR(ADCDATAL, 0x00, 0xFF);
  ret &= Agsi.WriteSFR(ADCDATAH, 0x00, 0xFF);
  ret &= Agsi.WriteSFR(DMAL,     0x00, 0xFF);
  ret &= Agsi.WriteSFR(DMAH,     0x00, 0xFF);
  ret &= Agsi.WriteSFR(DMAP,     0x00, 0xFF);

  return(ret);
}


extern "C" DWORD AGSIEXPORT AgsiEntry (DWORD nCode, void *vp) 
{
	CString tmp;

  switch (nCode) {
    case AGSI_CHECK:
      g_CpuType = *((DWORD *)vp);
      if (g_CpuType == 80166)
			{
				RX_REG=ASC1_RBUF;
				TX_REG=ASC1_TBUF;
				return(1);  // This driver supports the 8051 family of microcontrollers 
			}
      else if(g_CpuType == 8051) 
			{
				RX_REG=TX_REG=SBUF;
				return(1);
			}
			else
				return(0);  // Other microcontrollers are not supported by the driver
      break;

    case AGSI_INIT:                    // Declare all SFR's, VTREG's, Watches and Interrupts here
      AgsiConfig = *((AGSICONFIG *)vp);
//    AgsiConfig.m_hInstance;          // this pointer is used to get the function addresses of uVision
//    AgsiConfig.m_pszProjectPath;     // Path to application e.g. C:\KEIL\C51\EXAMPLES\HELLO
//    AgsiConfig.m_pszDevice;          // Simulated Device e.g. 52. This string is extracted out of the -p option.
//    AgsiConfig.m_pszConfiguration;   // complete dialog DLL options e.g. -p52 -dmydll ...
//    AgsiConfig.m_pszAppFile;         // name of loaded OMF file including path e.g. C:\KEIL\C51\EXAMPLES\HELLO\HELLO

      if (!GetFunctionPointers()) return(FALSE);   // get all function pointers for Agsi calls
     // if (!DefineAllSFR()) return(FALSE);          // define all special function registers
      if (!DefineAllVTREG()) return(FALSE);        // define all virtual registers
     // if (!DefineAllInterrupts()) return(FALSE);   // define all interrupts
		  if (!DefineAllWatches()) return(FALSE);      // define all watches
      if (!DefineAllMenuEntries()) return(FALSE);  // define all peripheral-menu entries and dialogs
			try
			{
				comPort.Open(g_strComm);
				listenPort.Open("com9");
				listenPort1.Open("com7");
		}
			catch (CException* e)
			{
				e->ReportError();
			}
      break;

    case AGSI_TERMINATE:               // Free all allocated memory, close all files ...
			tmp.Format("%d", g_FlashMemBase);
			Agsi.SetTargetKey ("FlashMemoryBase",tmp );      
			tmp.Format("%d", g_flashMemSize);
			Agsi.SetTargetKey ("FlashMemorySize",tmp );      
			Agsi.SetTargetKey ("flashDataFile",g_flashDataFile );   
			tmp.Format("%d", g_scanInterval);
			Agsi.SetTargetKey ("scaninterval",tmp );   
			Agsi.SetTargetKey ("commport",g_strComm );   
			break;

    case AGSI_RESET:                   // Reset all SFR's of this peripheral
     // if (!ResetPeripheral()) return(FALSE);
			Agsi.SetTimer(Timer, 10);
	  break;

    case AGSI_PREPLL:                  // Recalculate all peripherals before clock prescaler/PLL is set to a new value
      break;

    case AGSI_POSTPLL:                 // Recalculate all peripherals after clock prescaler/PLL is set to a new value
      break;
  }
  return(TRUE);       // return OK
}


// --------------------------------------------------------------------------------------------------
// Simulation of A/D Converter for ADuC812

static WORD newadcval  = 0;
static WORD adcdisable = 0;

static DWORD  adccon1,  adccon2,  adccon3,  adcdatal,  adcdatah,  dmal,  dmah,  dmap;   // Current values
static DWORD  adccon1p, adccon2p, adccon3p, adcdatalp, adcdatahp, dmalp, dmahp, dmapp;  // Previous values


void AdcConv(void) {
  union  fv   ain, temp, vref;
  static BYTE convstp = 1;
  DWORD  convst;
  DWORD  tdiff;
  BYTE   ChanID;
  DWORD  dmaaddress;

  if (adcdisable) return;
  adcdisable = 1;     	

  Agsi.ReadSFR(ADCCON1, &adccon1,  &adccon1p,  0xFF);
  Agsi.ReadSFR(ADCCON2, &adccon2,  &adccon2p,  0xFF);
  Agsi.ReadSFR(ADCCON3, &adccon3,  &adccon3p,  0xFF);
  Agsi.ReadSFR(DMAL,    &dmal,     &dmalp,     0xFF);
  Agsi.ReadSFR(DMAH,    &dmah,     &dmahp,     0xFF);
  Agsi.ReadSFR(DMAP,    &dmap,     &dmapp,     0xFF);
  Agsi.ReadVTR(CONVST,  &convst);

  if ((adccon3 ^ adccon3p) & 0x80) { // bit BUSY (in ADCCON3) is Read-Only
    adccon3 = adccon3p;
    initflag = 2;
  }

  if (adccon1 & 0xC0) {  // ADC enabled
	if ((adccon3 & 0x80) == 0) {  // no conversion in progress
	  if ((adccon2 & 0x30) ||                                                       // SCONV or CCONV
		  ((adccon1 & 0x01) && ((convstp & 0x01) == 0) && ((convst & 0x01) == 1)))  // CONVST pin: 0 -> 1
	  {  // starting new conversion
		adccon3 |= 0x80;                 // set BUSY
        if (adccon2 & 0x40) {            // DMA Mode
		  dmaaddress = dmal + (dmah << 8) + (dmap << 16);
		  Agsi.ReadMemory(dmaaddress, 1, &ChanID);
		  adccon2 = (adccon2 & 0xF0) | (ChanID >> 4);
		}
        if ((adccon2 & 0x0F) == 0x08) {  // Temperature sensor
          Agsi.ReadVTR(TEMP, &temp.DW);
          ain.f = 0.600f - (0.003f * (temp.f - 25.0f));
		}
		else {
		  if ((adccon2 & 0x0F) < 0x08) { // Analog inputs
            Agsi.ReadVTR(VTREG[adccon2 & 0x07].hVTR, &ain.DW);
		  } else ain.f = 0.0;
		}
        Agsi.ReadVTR(VREF, &vref.DW);
        newadcval = 0xFFFF;
        if (ain.f > vref.f) newadcval = 0x0FFF;
		if (ain.f < 0.0f)   newadcval = 0;
		if (newadcval == 0xFFFF) {
		  newadcval = (WORD)(ain.f * 4096.0f / vref.f + 0.5f);
		  if (newadcval > 0x0FFF) newadcval = 0x0FFF;
		}
		tdiff = ((17 + ((adccon1 & 0x0C) >> 2)) << ((adccon1 & 0x30) >> 4)) / 12;
		Agsi.SetTimer(Timer, tdiff);
	  }
	}
	else { // conversion in progress
	  if ((adccon2p & 0x20) && ((adccon2 & 0x20) == 0)) {  // end Continous Mode
	    adccon3 &= ~0x80;                  // clear BUSY
		Agsi.SetTimer(Timer, 0xFFFFFFFF);  // no time watch
	  }
	}
  }
  else {
    adccon3 &= ~0x80;                      // clear BUSY
	Agsi.SetTimer(Timer, 0xFFFFFFFF);      // no time watch
  }

  convstp = (BYTE)convst;

  Agsi.WriteSFR(ADCCON2, adccon2, 0x0F);
  Agsi.WriteSFR(ADCCON3, adccon3, 0x80);

  adcdisable = 0;
}

void AdcCompleted(void) {
  DWORD  dmaaddress;
  BYTE   dmadata[2];
  BYTE   ChanID;

  if (adcdisable) return;
  adcdisable = 1;     	

  Agsi.ReadSFR(ADCCON2, &adccon2, &adccon2p, 0xFF);
  Agsi.ReadSFR(ADCCON3, &adccon3, &adccon3p, 0x80);
  Agsi.ReadSFR(DMAL,    &dmal,    &dmalp,    0xFF);
  Agsi.ReadSFR(DMAH,    &dmah,    &dmahp,    0xFF);
  Agsi.ReadSFR(DMAP,    &dmap,    &dmapp,    0xFF);

  adcdatal = newadcval & 0xFF;
  adcdatah = (newadcval >> 8) | ((adccon2 & 0x0F) << 4);

  if (adccon2 & 0x40) {                   // DMA Mode
	dmaaddress = dmal + (dmah << 8) + (dmap << 16);
	dmadata[0] = (BYTE)(((adccon2 & 0x0F) << 4) | adcdatah);
	dmadata[1] = (BYTE)adcdatal;
	Agsi.WriteMemory(dmaaddress, 2, dmadata);
    dmaaddress += 2;
	dmal = (BYTE)(dmaaddress & 0xFF);
	dmah = (BYTE)((dmaaddress >> 8) & 0xFF);
	dmap = (BYTE)((dmaaddress >> 16) & 0xFF);
	Agsi.ReadMemory(dmaaddress, 1, &ChanID);
	if ((ChanID & 0xF0) == 0xF0) {        // DMA Stop
	  adccon2 = (adccon2 & 0xAF) | 0x80;  // clear DMA, SCON and set ADCI
	}
	else {
	  adccon2 = adccon2 & 0xEF;           // clear SCON
	}
    adccon3 = 0;                          // clear BUSY
  }
  else {
    adccon2 = (adccon2 & 0xEF) | 0x80;    // clear SCON and set ADCI
	adccon3 = 0;                          // clear BUSY
  }

  Agsi.WriteSFR(ADCCON2,  adccon2,  0xFF);
  Agsi.WriteSFR(ADCCON3,  adccon3,  0x80);
  Agsi.WriteSFR(ADCDATAL, adcdatal, 0xFF);
  Agsi.WriteSFR(ADCDATAH, adcdatah, 0xFF);
  Agsi.WriteSFR(DMAL,     dmal,     0xFF);
  Agsi.WriteSFR(DMAH,     dmah,     0xFF);
  Agsi.WriteSFR(DMAP,     dmap,     0xFF);

  Agsi.SetTimer(Timer, 0xFFFFFFFF);       // delete time watch

  adcdisable = 0;
  if (adccon2 & 0x20) AdcConv();          // continous conversion
}


/////////////////////////////////////////////////////////////////////////////
// CSPeriDLLApp construction

CSPeriDLLApp::CSPeriDLLApp()
{
	// TODO: add construction code here,
	// Place all significant initialization in InitInstance
}

/////////////////////////////////////////////////////////////////////////////
// The one and only CSPeriDLLApp object

CSPeriDLLApp theApp;

⌨️ 快捷键说明

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