2440串口移植的问题

asdfghjkl01   2009-12-24 20:16 楼主
2440 5.0 串口移植到 6.0。
加载串口驱动后,启动出现INFO: CReg2440Uart::CReg2440Uart using processor frequency reported by the OAL (0).
然后系统就死了。
也就是这一段
CReg2440Uart::CReg2440Uart()中
    if (!KernelIoControl(IOCTL_PROCESSOR_INFORMATION, NULL, 0, &procInfo, sizeof(PROCESSOR_INFO), &dwBytesReturned))
    {
        m_s3c2440_pclk = DEFAULT_S3C2440A_PCLK;
        RETAILMSG(TRUE, (TEXT("WARNING: CReg2440Uart::CReg2440Uart failed to obtain processor frequency - using default value (%d).\r\n"), m_s3c2440_pclk));
    }
    else
    {
        m_s3c2440_pclk = procInfo.dwClockSpeed;
        RETAILMSG(TRUE, (TEXT("INFO: CReg2440Uart::CReg2440Uart using processor frequency reported by the OAL (%d).\r\n"), m_s3c2440_pclk));
    }
问题是KernelIoControl 通过OALIoCtlProcessorInformation 这个函数获取信息。为什么 procInfo.dwClockSpeed 会是0?是获取失败么? 要怎么改?  

回复评论 (16)

难!!
点赞  2009-12-24 21:43
没有碰到过,帮顶,增加曝光率,哈哈哈
点赞  2009-12-24 22:54

4楼 斯蒂芬的 该用户已被删除

提示: 作者被禁止或删除 内容自动屏蔽
点赞  2009-12-24 23:27
呵呵 。。还在啊。。同祝。
点赞  2009-12-25 01:07
KernelIoControl会调用OEMIoControl, 你的OEMIoControl是怎么实现的?里面包含了读取外设时钟的代码吗?
我手头上的是没有实现的.

  1. case IOCTL_PROCESSOR_INFORMATION:
  2.         if (!lpOutBuf) {
  3.             SetLastError(ERROR_INVALID_PARAMETER);
  4.             return FALSE;
  5.         }
  6.    
  7.         if (sizeof(PROCESSOR_INFO) > nOutBufSize) {
  8.             SetLastError(ERROR_INSUFFICIENT_BUFFER);
  9.             return FALSE;
  10.         } else {
  11.             const WCHAR OEMProcCore[] = L"ARM";
  12.             const WCHAR OEMProcName[] = L"ARM920";
  13.             const WCHAR OEMProcVendor[] = L"SAMSUNG";
  14.             PPROCESSOR_INFO pProcInfo = (PPROCESSOR_INFO)lpOutBuf;
  15.    
  16.             if (lpBytesReturned) *lpBytesReturned = sizeof(PROCESSOR_INFO);
  17.             memset(pProcInfo, 0, *lpBytesReturned);
  18.                    
  19.             pProcInfo->wVersion = 1;
  20.                            
  21.             memcpy(pProcInfo->szProcessCore, OEMProcCore, (strlenW(OEMProcCore) + 1) * sizeof(WCHAR));
  22.             memcpy(pProcInfo->szProcessorName, OEMProcName, (strlenW(OEMProcName) + 1) * sizeof(WCHAR));
  23.             memcpy(pProcInfo->szVendor, OEMProcVendor, (strlenW(OEMProcVendor) + 1 ) * sizeof(WCHAR));
  24.    
  25.             pProcInfo->dwInstructionSet = 0;
  26.    
  27.             return TRUE;
  28.         }


不过即使没有实现也不会出现死机的现象啊,你看看是不是后面的函数有什么问题.
点赞  2009-12-25 09:32
引用: 引用 7 楼 flandy1982 的回复:
KernelIoControl会调用OEMIoControl, 你的OEMIoControl是怎么实现的?里面包含了读取外设时钟的代码吗?
我手头上的是没有实现的.
C/C++ codecase IOCTL_PROCESSOR_INFORMATION:if (!lpOutBuf) {
            SetLastError(ERROR_INVALID_PARAMETER);return FALSE;
        }if (sizeof(PROCESSOR_INFO)> nOutBufSize) {
            SetLastError(ERROR_INSUFFICIENT_BUFFER);return FALSE;
        }else {const WCHAR OEMProcCore[]= L"ARM";const WCHAR OEMProcName[]= L"ARM920";const WCHAR OEMProcVendor[]= L"SAMSUNG";
            PPROCESSOR_INFO pProcInfo= (PPROCESSOR_INFO)lpOutBuf;if (lpBytesReturned)*lpBytesReturned=sizeof(PROCESSOR_INFO);
            memset(pProcInfo,0,*lpBytesReturned);
            
            pProcInfo->wVersion=1;
               
            memcpy(pProcInfo->szProcessCore, OEMProcCore, (strlenW(OEMProcCore)+1)*sizeof(WCHAR));
            memcpy(pProcInfo->szProcessorName, OEMProcName, (strlenW(OEMProcName)+1)*sizeof(WCHAR));
            memcpy(pProcInfo->szVendor, OEMProcVendor, (strlenW(OEMProcVendor)+1 )*sizeof(WCHAR));
   
            pProcInfo->dwInstructionSet=0;return TRUE;
        }

不过即使没有实现也不会出现死机的现象啊,你看看是不是后面的函数有什么问题.

我的意見和ls這位牛人的意見是類似的。
不過我感覺你那個地方返回0有點問題。。。clockspeed是0.。。很奇怪了。。應該會有點值才對。
可能我對這個clockspeed的理解有錯誤
点赞  2009-12-25 10:03
帮顶,应该是相关的OEM函数没有实现
点赞  2009-12-26 17:02
引用: 引用 3 楼 xumercury 的回复:


这样我也改过,还是一样挂。
点赞  2009-12-25 00:36
引用: 引用 4 楼 wndce 的回复:
引用 3 楼 xumercury 的回复:


这样我也改过,还是一样挂。

那要一步步追下去了。。。太晚了。明天再看。。圣诞快乐。
点赞  2009-12-25 01:03
友情帮顶。
点赞  2010-1-6 13:28
地址映射好像没有出错
点赞  2010-1-6 14:55
过了一个星期,今天又拿出来调了下
BOOL   CReg2440Uart::Init()
{
    if (m_pReg) { // Set Value to default.       
        Write_ULCON(0);
        Write_UCON(0);
        Write_UFCON(0);
        Write_UMCON(0);
        return TRUE;
    }
即到这里首次写寄存器 就死了。。
m_pReg 是在 MapHardware()函数里面实现虚地址映射的

  1.     if (TranslateBusAddr(m_hParent,(INTERFACE_TYPE)dwi.dwInterfaceType,dwi.dwBusNumber, ioPhysicalBase,&inIoSpace,&ioPhysicalBase)) {
  2.         // Map it if it is Memeory Mapped IO.
  3.         m_pRegVirtualAddr = MmMapIoSpace(ioPhysicalBase, dwi.memWindows[0].dwLen,FALSE);
  4.                 RETAILMSG(1, (TEXT("dwi.memWindows[0].dwBase TranslateBusAddr successfully.m_pRegVirtualAddr: %X !\n"), m_pRegVirtualAddr));
  5.     }
.
dwi.memWindows[0].dwBase 打印出来 为50000000 即UART 控制寄存器的首地址。
m_pRegVirtualAddr 为D0500000,也是m_pReg的值,感觉是不是这里 地址映射出错了???
点赞  2010-1-5 15:34
沉得好快哦,顶下。
点赞  2010-1-7 11:23
晕哦, 还没人。
点赞  2010-1-9 16:11
收藏下, 明天再看。
点赞  2010-1-12 22:49
我也收藏下,有空自己研究与学习下。
点赞  2010-1-12 20:09
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 京公网安备 11010802033920号
    写回复