Wednesday, September 10, 2008

WinCE 5.0 bug on persistent storage

The files in the recycle bin can not be restored after a hard reset. It is a Microsoft bug.

交叉编译qt-embedded-free-3.3.8 (转贴)

我是用qt-embedded-free-3.3.4


交叉编译环境:
HOST操作系统:Linux-2.6.15-1.2054_FC5-GCC版本-4.1.0
TARGET:mx31开发板(freescale-ARM11平台)
交叉编译工具链:arm-none-linux-gnueabi(mx31开发板所提供) gcc-4.1.1
Qt/E版本:qt-embedded-free-3.3.8
(ps:HOST上已经编译过qt-embedded-free-3.3.8---gcc 4.1.0)

下面的过程是在HOST-PC上已经正确的安装了qt-embedded-free-3.3.8上进行的:

交叉编译的详细步骤:
第一步:下载qt-embedded-free-3.3.8并解压缩到自定义的目录下。

我的目录是
tar jxvf qt-embedded-free-3.3.8.tar.bz2
自动生成 /root/qt/qt-embedded-free-3.3.8
(注意:记得将你在HOST编译好的QT/E的目录下的bin文件里的moc和uic二进制文件copy到我们交叉编译的目录下的bin文件夹里-就是/root/qt/qt-embedded-free-3.3.8)

注:moc and uic 应该是由qt-x11-free-3.3.8编译生成的。因为我使用 qt-x11-free-3.3.4所以要

./configure -no-xft. 3.3.5 should not have such problem.



第二步:安装交叉编译工具链
这一步取决于你所使用的交叉编译工具链,我的是arm-none-linux-gnueabi(freescale的mx31开发板所提供)

安装完成后bin的目录是:
/opt/freescale/usr/local/gcc-4.1.1-glibc-2.4-nptl-6/arm-none-linux-gnueabi/bin

第三步:配置qmake(即指定交叉编译工具)
在mkspecs/qws/下建立arm-none-linux-gnueabi目录
cd /root/qt/qt-embedded-free-3.3.8
cd mkspecs/qws/
mkdir arm-none-linux-gnueabi

把mkspecs/qws/linux-arm-g++下的qmake.conf和qplatformdefs.h复制到mkspecs/qws/arm-none-linux-gnueabi目录下

然后修改qmake.conf文件,把文件里面的编译器指定为arm-none-linux-gnueabi

用arm-none-linux-gnueabi-gcc和arm-none-linux-gnueabi-g++替代以下的arm-linux-gcc和arm-linux-g++

QMAKE_CC = arm-linux-gcc
QMAKE_CXX = arm-linux-g++
QMAKE_LINK = arm-linux-g++
QMAKE_LINK_SHLIB = arm-linux-g++

第四步:环境变量的设置
export QTEDIR=/root/qt/qt-embedded-free-3.3.8
export QTDIR=$QTEDIR
export PATH=/opt/freescale/usr/local/gcc-4.1.1-glibc-2.4-nptl-6/arm-none-linux-gnueabi/bin:$PATH
export PATH=$QTDIR/bin:$PATH
export LD_LIBRARY_PATH=$QTDIR/lib:$LD_LIBRARY_PATH

第五步:config
./configure -xplatform qws/arm-none-linux-gnueabi -no-cups -no-stl -no-qvfb -depths 4,8,16,32 -qt-gif -embedded arm -disable-sql

注意:在configure的时候会出现一个警告
WARNING: Failure to find: .moc/release-static-mt-emb-x86/allmoc.cpp

关于这个问题官方已经给出答案,引用如下
This is not a problem. It happens everytime Qt/embedded is configured.
所以,这个警告可以不预理会。

第六步:make 或者是 make sub-src
make/make sub-src

注意:make的时候由于对于qt3的交叉编译工具的gcc版本问题而导致提示如下错误:

../include/qstring.h: In member function 'ushort& QChar::unicode()':
../include/qstring.h:199: error: cannot bind packed field
'((QChar*)this)->QChar::ucs' to 'ushort&'

解决办法:
打开src/tools/qglobal.h查看318-326行:
# if (defined(__arm__) || defined(__ARMEL__)) && !defined(QT_MOC_CPP)
# define Q_PACKED __attribute__ ((packed))
# if __GNUC__ == 3 && __GNUC_MINOR__ >= 4
# define Q_NO_PACKED_REFERENCE
# endif
# endif
# if !defined(__EXCEPTIONS)
# define Q_NO_EXCEPTIONS
# endif

修改如下:
# if (defined(__arm__) || defined(__ARMEL__)) && !defined(QT_MOC_CPP)
# define Q_PACKED __attribute__ ((packed))
# if __GNUC__ == 3 && __GNUC_MINOR__ >= 4
# define Q_NO_PACKED_REFERENCE
# endif
+# if __GNUC__ == 4 && __GNUC_MINOR__ >= 0
+# define Q_NO_PACKED_POINTERS
+# endif
# endif
# if !defined(__EXCEPTIONS)
# define Q_NO_EXCEPTIONS
# endif

打开src/include/qstring.h查看195-199行
ushort unicode() const { return ucs; }
#ifdef Q_NO_PACKED_REFERENCE
ushort &unicode() { return *(&ucs); }
#else
ushort &unicode() { return ucs; }
#endif

修改如下:
ushort unicode() const { return ucs; }
#ifdef Q_NO_PACKED_REFERENCE
ushort &unicode() { return *(&ucs); }
+#elif defined Q_NO_PACKED_POINTERS
+ ushort &unicode() { ushort& tmp = ucs; return tmp; }
#else
ushort &unicode() { return ucs; }
#endif

ps:+号表示修改的地方

接下来就是make clean
make

第七步 strip
交叉编译成功后在/lib文件夹下生成以下文件:
libqte-mt.so
libqte-mt.so.3
libqte-mt.so.3.3
libqte-mt.so.3.3.8

[root@localhost lib]# ls -l
lrwxrwxrwx 1 root root 18 09-05 17:25 libqte-mt.so -> libqte-mt.so.3.3.8
lrwxrwxrwx 1 root root 18 09-05 17:25 libqte-mt.so.3 -> libqte-mt.so.3.3.8
lrwxrwxrwx 1 root root 18 09-05 17:25 libqte-mt.so.3.3 -> libqte-mt.so.3.3.8
-rwxr-xr-x 1 root root 7091636 09-07 08:51 libqte-mt.so.3.3.8

我们先来查看文件信息:
[root@localhost lib]# file libqte-mt.so.3.3.8
libqte-mt.so.3.3.8: ELF 32-bit LSB shared object, ARM, version 1 (SYSV), not stripped

此时显示的是not stripped,即没有经过strip。

[root@localhost lib]# arm-none-linux-gnueabi-strip libqte-mt.so.3.3.8

执行strip命令之后我们再次查看文件信息:
[root@localhost lib]# file libqte-mt.so.3.3.8
libqte-mt.so.3.3.8: ELF 32-bit LSB shared object, ARM, version 1 (SYSV), stripped

此 时显示的是stripped,即已经strip。你会发现,strip之后libqte-mt.so.3.3.8发生明显变化的,不过在实际的开发过程 中,我们是不提倡这样做的,因为使用strip后,使用gdb时就无法获得调试信息了。故,在开发过程,我们为了方便以后的调试最好不要strip。

后 记:因为是初步交叉编译,所以触摸屏支持和字体库的添加,中文支持,如何添加wenquanyi字体等等,还有库的裁减都没有具体实现,不过完成后我会继 续写出来,与大家分享!另外,很多地方我懒得注释,因为很多知识都是交叉编译的基础只是,请读者自己理解!这也是一个学习的过程。

Wednesday, July 2, 2008

active sync problem on WinCE 5.0 persistent storage

The File Synchronization problem in the persistent storage is confirmed to be the Microsoft bug. It is solved in WinCE 6.0. According to the below link, Microsoft said they had the solution for WinCE 5.0. But I can't find it from their updates. Maybe in the near future, they will release the solution.

http://msdn.microsoft.com/en-us/library/ms885839.aspx
http://msdn.microsoft.com/en-us/library/aa911937.aspx
http://msdn.microsoft.com/en-us/library/aa912073.aspx

To future engineer (zt)

看这篇帖子的,我想都是电子爱好者或电类专业学生。不知道大家都处于什么一个阶段,这篇帖子是写给入门者的,要解决一个问题:初学者应重点掌握什么电子知识,大学阶段如何学习?

先说点貌似题外的东西——3个谬论。

谬论一:高中老师常对我们说,大家现在好好学,考上了大学就轻松了,爱怎么玩怎么玩。这真是狗屁。别的专业我不好说,电气、电子、电力、通信、自动化等电类专业,想要轻松那是不可能地(当然你是天才就另说),专业课上讲的东西对决大多数人来说那是云里雾里,从来都是一知半解,需要你课下花大量时间精力来消化。有些东西甚至需要你若干年后在工作中遇着时才回过味:“哦,原来以前学的那东西是干这使的。”你要能想得起,并知道怎么回头去补,就算是上学时专业课学得较扎实了。

谬论二:填志愿时经常有人对我们说:专业不重要,学校最重要,进了个好学校想学什么再学。这亦是狗屁。进了学校,本专业的课程就可能会压得你喘不过气来,还有多少人有时间和毅力选修第二专业?而所学专业几乎就是决定了你今后一生的职业生涯。而学校,说实话本科阶段从老师那学到的东西各校间差别不是很大。课上讲的大同小异,课下也不会有什么好老师给你单独指导和点拨(若能遇着,那是你的幸运)。越牛的学校的越牛的老师就越忙,不要指望他们会在教学上花多少心思,更不要指望他们对你另眼相看。反倒是一些普通院校的小老师们可能跟学生走得更近,辅导更多些,虽然他们可能水平一般,但对于你大学的学习来说还是足够的。综上所述,我觉得对于一个电子爱好者来说,成为一名普通重点大学的电子系学生比成为北大的哲学系学生更重要。当然看帖的应该大多数都是学电的,那恭喜你,这个专业不错的,虽不是什么“朝阳产业”,但绝对是个“常青行业”。

谬论三:上了大学,可能又有不少人对你说,在大学专业不重要,关键的是学好计算机和英语,这样就不愁找不到好工作了。这也是屁话。你要明确一点:你将来不是纯靠英语吃饭的,也不是做编程、搞软件开发或动画创作的。我是想说:若果你性格偏内向沉稳、肯钻研、爱好电子行业,将来想从事电子设计和研发工作,那你一定要学好专业课。当然英语也很重要,但以后工作中用得多的是你的专业英语,即能读懂英语技术文档,而不是跟别人比你口语多正宗多流利。至于计算机,那就是一工具,不要花太多时间去学photoshop3dmaxFlash、网页制作等流行软件,这些在你今后的工作中用不着,也会牵扯你大量时间精力。好钢用在刀刃上,多进进实验室多搭搭电路吧。当然,电类学生对电脑也有特殊要求,那就是用熟ProtelMultisim,学好汇编语言、C语言、选学PLD相关软件。任务也是很重的。

以上说了3个谬论,下面言归正传吧。那么进了大学,读了电类专业,这4年你该学些什么呢?

1. 大一大二(打基础)

首先要了解:电类专业可分为强电和弱电两个方向,具体为电力工程及其自动化(电力系统、工厂供变电等)专业属强电,电气工程及其自动化以强电为主弱电为辅,电子、通信、自动化专业以弱电为主。其他更进一步的细分要进入研究生阶段才划分。但无论强电还是弱电,基础都是一样的。

首先高数是要学好的,以后的信号处理、电磁场、电力系统、DSP等不同方向的专业课都用得着。

专业基础课最重要的就是电路分析、模拟电路、数字电路。这3门课一定要学好。这3门课一般都是大一下学期到大三上学期开设,对大多数对电子知识还了解不多的同学来说,通常是学得一知半解,迷迷糊糊。所以,最好是在开课之前或是开课的同时读一两本通俗浅显的综合介绍电子知识的书籍,对书中的知识你不需要都懂,能有个大致感觉就行。对这这种入门读物的选择很重要,难了看不懂可能兴趣就此丧失或备受打击,反而事与愿违。在此推荐一本《电子设计丛零开始》(杨欣编著,清华大学出版社出版),该书比较系统全面地介绍了电子设计与制作的基础知识,模电、数电、单片机、Multisim电路仿真软件等都有涉及,一册在手基本知识就差不多了,关键是浅显易懂,有一定趣味性。另外科学出版社引进出版的一套小开本(32开)电子系列图书也不错,是日本人写的,科学出版社翻译出版,插图较多,也较浅显,不过这一系列分册较多,内容分得较细。

除了看书,还要足够重视动手实践。电路、模电、数电这些课程进行的同时都会同时开设一些试验课,珍惜这个动手机会好好弄一弄,而不要把它当作一个任务应付了事。跟抄作业一样,拷贝别人的试验结果在高校中也是蔚然成风,特别是几个人一个小组的实验,那就是个别勤奋好学的在那折腾,其他人毫不用心地等着出结果。我只想说,自己动手努力得来的成果才是甜美的,那种成就感会让你充实和满足。游手好闲的,到临近毕业找工作或在单位试用时,心中那种巨大的惶恐会让你悔不当初。这种教训太多了,多少次我们都是蹉跎了岁月才回过头来追悔莫及。除了实验课好好准备好好做之外,许多学校都设有开放性实验室,供学生平时课余自觉来弄弄。珍惜这种资源和条件吧,工作后不会再有谁给你提供这种免费的午餐了。当然有些学校没有这么好的条件,或缺少器件,那同学们就在电脑上模拟一把试验平台吧,就是学好用好Multisim软件。Multisim是一种电路仿真软件,笔者上学时叫做EWB,后来随着版本更新,先后更名为Multisim2001Multisim7Multisim8。这个软件可模拟搭建各种模拟电路和数字电路,并可观测、分析电路仿真结果。大伙可以把模电、数电中学习的电路在这软件里面模拟一下,增加感性认识,实验前后也可把试验电路在软件里模拟,看跟实际试验结果有多大差别。可以说,只要你是学电的,这个小软件就是你上学时必须掌握的,对你的学习助益很大。另一个必须掌握的软件那就是protel了。上学时,从小学期的综合设计实验到毕业设计,最后都会要求你用Protel绘出设计的电路原理图和PCB版;工作后,Protel也是你必须掌握的基本技能,部分同学毕业后一两年内的工作,可能就是单纯地用这软件画板子。Protel的版本也走过了Protel98Protel99Protel99SEProtelDXPProtel2004的发展道路。Protel99SEProtelDXPProtel2004这三个版本现在用得最多,目前许多学校教学或公司内工程师使用的都还是Protel99SE,当然若作为新的自学者直接从Protel2004学起似乎好一些。综上所叙,作为最基本的EDA(电子设计自动化)软件,MultisimProtel是所有电类学生在上学时必须掌握的。其他的如PspiceOrcadSYstemviewMATLABQuartusII等等,需根据不同的专业方向选学,或是在进入研究生阶段或工作后在重点学习使用。那MultisimProtel好学么?入门应该问题不大,让师兄师姐指导指导,或是找一两本入门书看一看就OK了。这里推荐一本《电路设计与仿真——基于Multisim 8Protel 2004》(也是杨欣编著,清华社出版),作为这两款软件的入门学习挺不错的,关键是一本书包含了两款软件学习,对穷学生来说比较划算,若是花钱买两本书分别去学这两个软件,就不值了,因为Multisim的入门不是很难。另用ProtelPCB电路板学问挺大的,有必要多看一些技术文档或是买一本高级应用类的图书。

2.大三大四(学习专业课,尝试应用)

进入大三,就涉及到专业课的学习了,本文只讨论以应用为主的专业课,其他如《电力系统分析》、《电机学》、《自控原理》、《信号与处理》、《高电压》、《电磁场》等等以理论和计算为主的专业课,咱就不多提了。当然这些课对你今后向研究型人才发展很重要,也都很让人头疼,要有建议也只能说是努力学、好好学,懂多少是到少(不过别指望全都懂),以后工作或接着深造用得着时再回过头来接着补接着学,那时有工作经验或接触多了有感性认识,可能学着就容易些了。

那以应用为主的专业课又有哪些呢?不同专业方向有不同的课程,很难面面俱到。这里先简单罗列一下,有微机原理与接口技术(也称单片机)、开关电源设计、可编程逻辑器件(PLD)应用、可编程逻辑控制(PLC)应用、变频器应用、通信电路、数字集成电路分析与设计、DSP、嵌入式等等。可能有同学要问:这么多东西,大学阶段要想都学好不容易吧?答案是不仅是不容易,而且是不可能。这些技术每一门展开来都是复杂的一套知识,可以说,你只要精通其中一门,就可以到外边找个不错的工作了。而且在大学阶段,这些课程也不是都要学的,而是针对不同专业方向选修其中几门(具体选哪几门,多研究研究你们各自的专业培养方案,多请教老师),学的时候争取能动基本用法即可,真正的应用和深入是要到工作后的;当然你若很勤奋或有天赋,能熟练掌握某一门达到开发产品的程度,那毕业后找个好工作就轻而易举了。到这里我们需要再明确一点:电子领域知识繁多、浩如烟海,所以一般搞硬件的公司都有较多的员工,一个研发项目是多人细致分工、共同完成的,所以我们经常会听到团队意识这个名词。因为一个人的能力有限,不可能掌握所有的知识。比如一些人专门负责搞驱动,一些人专门从事逻辑设计,一些人专门搞高频无线,一些人专门搞测试,一些人专门设计外壳,一些人专门设计电路板等等。

看到这里可能有的同学头都大了:那说来说去大学阶段到底究竟应该学些什么呢?说实话写到这里我的头也大了,电子设计涉及方方面面的东西太多了,实在不是一篇文章甚至一本书能说得清楚的。所以我决定剔除这些生涩的课程名目,大致说一下我所认为的一个电类学生或是想要成为电子工程师的自学者应该掌握的基本的专业技能。

我认为:除了最初提到的电路分析、模拟电路、数字电路基础知识外,应了解并掌握电子元器件识别与选用指导、基本仪器仪表的使用、一些常用电路模块的分析与设计、单片机的应用、PLD的应用、仿真软件的应用、电路板设计与制作、电子测量与电路测试。

电子元器件的识别与使用就不用说了,这是元素级的基础,不过要想掌握好也并不容易,一些电子系学生毕业了,还认不出二极管、三极管实物、分不清电解电容的正负极等等,也不是没有的事。还是一句话,多进进实验室,多跑跑电子市场,多看看书。

仪器仪表的使用,大学的实验课中你至少会用过数字万用表,波形发生器、电源、示波器、小电机、单片机仿真机,至少要把这些东西的接线方法和用法弄懂吧。

常用电路模块也是包罗万相,各种放大电路、比较器、AD转换电路、DA转换电路、微分电路、积分电路,还有各种数字逻辑单元电路等等,只能说,大致了解吧,并学会怎么去查资料、查芯片查管脚。最基本的,做实验或课程设计中用到的各种芯片要弄熟。

单片机,这是应该掌握的。时下单片机种类繁多,但各大小企业用得最多的还是51系列单片机,而且价格便宜、学习资料也最全,故给自学者推荐。当然各学校开课讲的单片机型号会有所不同,没关系,学好单片机编程,学好了一种,再学别的单片机就容易了。

PLD(可编程逻辑器件),一种集成电路芯片,提供用户可编程,实现一定的逻辑功能。对可编程逻辑器件的功能设定(即要它实现什么功能)要有设计者借助开发工具,通过编写程序来实现,这跟单片机类似。开发工具可学习Altera公司的Quartus II软件(这是该公司的第4PLD开发软件,第3代是MAX+PLUS II软件)。编程语言学习硬件描述语言VHDLVerilog HDL

仿真软件最基本的就是前面说的Multisim了,另外还可学MATLAB。其他的试专业情况选学或是工作后学。电路板设计与制作主要是用Protel软件辅助进行。这在前面已有介绍,读者应该也比较熟悉。

最后建议同学们积极与各类电子竞赛赛事,参加一场比赛一个项目做下来,电子设计的一个流程和各环节的基础知识就能串起来了,对知识的融会贯通及今后走向工作岗位都有莫大裨益。

以上这些东西我说得笼统,深入下去又是一大堆要学的东西。还是那句话,多啃书本、多实践!清华大学出版社有一套“电子电路循序渐进系列教程”是按照上面我所讲的那个思路出的,可惜还没出全,现在好像只有《单片机在电子电路设计中的应用》、《电路设计与制板——Proetl应用教程》、《仿真软件教程——MultisimMATLAB》、《常用电路模块分析与设计指导》几本。另外听听你们老师的意见、师兄师姐的意见,问问他们应读些什么书。当然也不能尽听尽信,翻开一本书我想你先大致看看他讲得是否通俗,自己琢磨着能看懂几分?我想能有5分懂这本书就值得一看了,示自己现阶段的知识情况,太浅显的书不用看了,太深的书也不要去看,看得迷迷糊糊还打击自信心丧失了兴趣。

好了,就此停笔吧。本来是要写个书目推荐,可干瘪瘪的罗列一堆书目有什么意义?还是写下这些字,让同学们自己去思考去选择去深入吧,希望能对你们有所帮助。

最后一句老生常谈也是我的切肤之痛:大学四年会一晃而过,要学的东西太多太多,不要虚度光阴。及时当努力,岁月不待人!

Bill Gate retired on June 28th, 2008 (zt)

明天,6月28日,全球将正式步入PC操作系统的后盖茨时代



北京时间6月27日12:00消息(美国东部时间6月27日00:00),微软创始人、董事长比尔·盖茨(Bill Gates)将于今日正式退休,淡出微软日常管理工作。现任CEO、盖茨大学好友史蒂夫·鲍尔默(Steve Ballmer)将全面接掌微软大权。

比尔·盖茨将把自己580亿美元财产全数捐给其名下慈善基金“比尔及梅琳达盖茨基金会”(Bill & Miranda Gates Foundation),一分一毫也不会留给自己子女。 同时,盖茨本人也将全身心投入到慈善事业中。据海外媒体报道,盖茨曾表示,做为全职慈善家,他要去的第一个站就是中国。

从技术强人到道德圣人,盖茨给我们留下了很多值得学习的东西。这里一起分享一下他的十条职场箴言:
  1.生活是不公平的,要去适应它;
  2.这世界并不会在意你的自尊,这世界指望你在自我感觉良好之前先要有所成就;
  3.高中刚毕业你不会成为一个公司的副总裁,直到你将此职位挣到手;
  4.如果你认为你的老板严厉,等你当了老板再这样想;
  5.如果你陷入困境,不要尖声抱怨错误,要从中吸取教训;
  6.在你出生之前,你的父母并非像现在这样乏味。他们变成今天这个样子是因为这些年来他们一直在为你付账单,给你洗衣服,听你大谈你是如何的酷;
  7.你的学校也许已经不再分优等生和劣等生,但生活却仍在作出类似区分;
  8.生活不分学期,你并没有暑假可以休息,也没有几个人乐于帮你发现自我;
  9.电视并不是真实的生活,在现实生活中,人们实际上得离开咖啡屋去干自己的工作
  10.永远不要在背后批评别人,尤其不能批评你的老板无知、刻薄和无能。(因为这样的心态,会使你走上坎坷艰难的成长之路)。

exective meeting 2008

To reiterate, the take-away message for the team building activities :-

1. Puzzle

· The activity is one of cooperation not competition

· The theme of this activity demonstrate that all the people and all the teams make up the whole, and no team or individual can do it alone – likewise in a company

2. Road Map

· The theme focuses on communication and decision-making in a team to arrive at the ultimate decision where everyone is in agreement – working together

BOM of 3G iPhone

Monday, June 2, 2008

TT750 USB sync not stable bug

// remove the below code from VbusHandler(void) function.
//don't understand why need to make 5000ms and reconnect again.

#if 0
Sleep(5000);

if(IsVbusOn())
SetInterruptEvent(SYSINTR_VBUS);
else
SetVbusInterrupt(FALSE);
#endif

TT750 SD card multithread problem

/* Add the retry scheme to solve the SD card multithread problem */
// This bug looks like Freescale SD module or DMA module bug.
/*---------------------------------------------------------------------------*/
// Read multiple block from MMC card.
BOOL MMCSD_ReadMultipleBlock(TMMCSD_CardInformationStructure *pCIS, DWORD dwAddress, void *pBuffer, DWORD dwLength)
{
TMMCSD_Reg *pMMCSD;
int ii;
//hf++ 20060503
volatile int dwTimeout=0;
BYTE * pbtDataBuffer = (BYTE*)pBuffer;
int retry=0;
int blRetValue = 0;
//hf-- 20060503

RETAILMSG(MMCSD_DEBUG_MSG, (TEXT("MMCSD_ReadMultipleBlock+, Address:0x%x, Size:0x%x\r\n"), dwAddress, dwLength));
RETAILMSG(MMCSD_DEBUG_MSG, (TEXT("Size:0x%x\r\n"), dwLength));
for (retry = 0; retry<3;retry++)
{
if (retry !=0)
RETAILMSG(1, (TEXT("MMCSD_ReadMultipleBlock retry=0x%x\r\n"), retry));
if (blRetValue!=0)
{
RETAILMSG(1, (TEXT("MMCSD_ReadMultipleBlock retry reason=0x%x\r\n"), blRetValue));
}
blRetValue = 0;
pMMCSD = gpMMCSD;
pbtDataBuffer = (BYTE*)pBuffer;
#if 0
// Activate card.
if (pCIS->CardType == MMCSD_CardMMC) {
if (!MMCSD_MMC_SelectCard(pMMCSD, pCIS->dwRCA)) {
return FALSE;
}
}
else if (pCIS->CardType == MMCSD_CardSD) {
if (!MMCSD_SD_SelectCard(pMMCSD, pCIS->dwRCA)) {
return FALSE;
}
}
else {
return FALSE;
}
#endif

//hf++ 20060503 add timeout
// Make sure card is ready to transfer
dwTimeout = 0;
while ((!MMCSD_IsReady(pMMCSD, pCIS))&&(dwTimeout Sleep(0);
dwTimeout++;
}
if (dwTimeout>=MMC_SD_TIMEOUT)
{
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: IsReady Timeout1\r\n")));
blRetValue = 1;
continue;
}

//hf-- 20060503

// Set hardware transfer dwLength register.
MMCSD_SetTransferLength(pMMCSD, MMCSD_DATA_BLOCK_LENGTH);

// Set block dwLength for transaction.
if (!MMCSD_SendCMD16(pMMCSD, MMCSD_DATA_BLOCK_LENGTH)) {
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: MMCSD_SendCMD16 Failed!\r\n")));
blRetValue = 2;
continue;
}

//hf++ 20060503 add timeout
// Make sure card is ready to transfer
dwTimeout = 0;
while ((!MMCSD_IsReady(pMMCSD, pCIS))&&(dwTimeout Sleep(0);
dwTimeout++;
}
if (dwTimeout>=MMC_SD_TIMEOUT)
{
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: IsReady Timeout2\r\n")));
blRetValue = 3;
continue;
}
//hf-- 20060503

if (pCIS->CardType == MMCSD_CardSD) {
MMCSD_SD_SetBusWidth(pMMCSD, pCIS->dwRCA, MMCSD_BusWidth4Bit);
}
else {
MMCSD_MMC_SetBusWidth(pMMCSD);
}

MMCSD_SetBlockNumber(pMMCSD, dwLength/MMCSD_DATA_BLOCK_LENGTH, MMCSD_DatModeDataReceiveStart);
// Send read multiple block command.
if (!MMCSD_SendCMD18(pMMCSD, dwAddress)) {
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: MMCSD_SendCMD18 Failed!\r\n")));
blRetValue = 4;
continue;
}

//MMCSD_SetClock(pMMCSD, MMCSD_ClockStart);
//pMMCSD->STR_STP_CLK = 0x06;

// Copy data from card.
for (ii=dwLength/MMCSD_DATA_BLOCK_LENGTH; ii>0; ii--) {
if (!MMCSD_ReceiveSingleBlock(pMMCSD, (BYTE*)pbtDataBuffer, MMCSD_DATA_BLOCK_LENGTH)) {
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: MMCSD_ReceiveSingleBlock Failed!\r\n")));
blRetValue = 5;
continue;
}
pbtDataBuffer = (BYTE*)((DWORD)pbtDataBuffer + MMCSD_DATA_BLOCK_LENGTH);
}

// Send stop transmission command.
if (!MMCSD_SendCMD12(pMMCSD)) {
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: MMCSD_SendCMD12 Failed!\r\n")));
blRetValue = 6;
continue;
}

// Wait for transaction to complete.
// while (!MMCSD_IsDataTransferDone(pMMCSD)) {
// Sleep(0);
// }

// MMCSD_SetClock(pMMCSD, MMCSD_ClockStop);

#if 0
// Deactivate card.
MMCSD_DeselectCard(pMMCSD);
#endif
if (blRetValue == 0)
break;
//RETAILMSG(MMCSD_DEBUG_MSG, (TEXT("MMCSD_ReadMultipleBlock-\r\n")));
}
if ((retry!=0)&&(retry!=3))
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: recover by retry=%x\r\n"), retry));
if (retry == 3)
{
RETAILMSG(MMCSD_ERROR_MSG, (TEXT("MMCSD_ReadMultipleBlock: can't recover\r\n")));
return FALSE;
}

return TRUE;
}

SD card multi-thread problem

The guy have the similar problem. The bug doesn't solve when Do as he did.

http://www.tech-archive.net/Archive/WindowsCE/microsoft.public.windowsce.platbuilder/2007-07/msg00470.html

TT750 battery calibration

Main Battery
4.2V 986
4.10V 960
4.05V 948
4.00V 937
3.95V 924
3.90V 912
3.85V 903
3.80V 887
3.75V 876
3.70V 864
3.67V 857
3.647V 851
3.62V 844
3.6V 839
3.5V 814

The LCD backlight become consistent on PV1 and DV2

Backlight setting for DV2
feedback resistor is 7.5ohm

Level feedback voltage PMW value
0 19mV 0x1e
1 30mV 0x1d
2 41mV 0x1c
3 53mV 0x1b
4 64.6mV 0x1a
5 88mV 0x18
6 110mV 0x16
7 133mV 0x14
8 154mV 0x12

for PV1
The feedback resistor is 15ohm
0 37.9mV 0x2a
1 61.8mV 0x24
2 78.1mV 0x22
3 103mV 0x1F
4 127mV 0x1C
5 178mV 0x16
6 219mV 0x11
7 267mV 0x0B
8 290mV 0x07

Re-calibrate the battery ADC with the battery capacity.

For PV1 and DV2 main battery
4.2v 891 99%
4.10v 870 97%
4.05v 859 92%
4.00v 848 86%
3.95v 838 82%
3.90v 827 76%
3.85v 817 68%
3.80v 806 59%
3.75v 795 47%
3.70v 785 31%
3.67v 778 21%
3.647v 773 15%
3.62v 767 10%
3.60v 763 7% go to sleep
3.55v 753 5%
3.50v 742 4%

Secondary Battery
4.2v 880 100%
4.1v 861 99%
4.05v 851 98%
4.00v 840 96%
3.95v 830 88%
3.90v 819 84%
3.85v 806 79%
3.80v 798 71%
3.75v 786 63%
3.70v 774 54%
3.65v 765 37%

battery low at 781.

The dialer of HyperTty doesn't work in the debug version

Just found that the dialer of HyperTty doesn't work properly in the debug version. Why? Debug port is com1 (driver is mx21serial.dll) and dialer use com3 (driver is com16550.dll).

How to change Dial default location from "work" to "home"

[HKEY_CURRENT_USER\ControlPanel\Dial]
; What is Location ID (value name) for the current location
"CurrentLoc"=dword:1 ;0-work 1-home