1、序言 非接触式智能卡已经广泛地应用于各类门禁控制系统,公共交通支付系统,e-purse系统,高速公路不停车收费系统,IBMS(智能大楼管理系统),海关过境身份识别,以及医疗保险系统等等。 非接触式智能卡以其高度安全保密性,通信高速性,使用方便性,成本日渐低廉等而受到广泛使用,给我们的生活质量带来了很大的提高。因此,如何认识、理解智能卡,特别是带有非常神秘色彩的非接触式智能卡,已引起很多智能卡的使用者,包括智能卡专业研发的IT科研人员的极大的兴趣和爱好。笔者在此很愿意将自己多年来在智能卡(接触式智能卡及非接触式智能卡)方面的研究及其软硬件应用开发的经验与大家一同交流和分享,以取得我国金卡工程事业的更进一步的发展。 在此,笔者将以符合ISO/IEC14443TYPEA标准的Mifare1S50系列非接触式智能卡及其读写设备专用IC(ASIC)RC150/170模块为对象,与大家一起就“关于非接触式智能卡及其读写器ASIC模块之‘密码操作’”作一些研究与探讨,并将用标准的Intel-51系列微处理器汇编语言进行实际的应用程序的开发。在笔者曾设计和开发的众多智能卡项目中,本文所给出的应用程序都有着良好的运行效果。
2、非接触式智能卡及其读写器ASIC模块RC150/170 Mifare1S50非接触式智能卡片有着16个Sector(扇区);每个Sector包含4个Block(块);每个Block具有16个byte的存储容量。Sector被定义为Sector0至Sector15;Block被分为Block0至Block3;整个Mifare1S50非接触式智能卡共有64个Block。 Sector0中的Block0记录了该张智能卡的序列号(SerialNumber)以及生产厂商的标志信息等,这些信息已在卡片出厂时固化,不能更改。因此该Block不能再复用为应用数据块。 每个Sector中的Block3被特别用来存放对该Sector中应用块Block0,1,2及其本身Block3进行数据存取的密码及存取权限。整个Mifare1S50非接触式智能卡共有16个Block3。根据绝对地址编址,他们可被编为Block3(在Sector0中),Block7(在Sector1中),Block11(在Sector2中),以及Block63(在Sector15中)等等。 对于某一Sector中的Block3的绝对地址编址可以由下列公式计算得到: Block X=(N+1)*4-1 其中:X:绝对地址编址的Block块号 N:Sector扇号,0至15 通常每个扇区的Block0,1,2都存放着非常保密的数据,例如坐公交车/出租车前在公交公司指定地点已购买的车资钱款,智能大厦/智能小区进出时所需的控制信息,股票交易时持有股票交易智能卡片者必须对已存放在智能卡中的交易密码数据(例如帐户、存款信息、已买进股票数量/品种等等)进行确认,才能得以股票交易,等等。 由于每一个Block3中包含了该扇区的密码字节以及对该扇区中其余Block0,1,2进行数据处理的存取控制权限字节,因此如何操作处理Block3将是很重要的内容。以下将展开对每个扇区的Block3进行研究。 Block3有16个byte组成。前6个字节是密码A(KEYA),KEYA的缺省值可能为“A0A1A2A3A4A5”;最后6个字节是密码B(KEYB),KEYB的缺省值可能为“B0B1B2B3B4B5”;中间4个字节是控制字节,缺省值可能为“FFH07H80H69H”;利用KEYA或KEYB并遵守早已定义在4个控制字节中的存取条件,我们便能对该密码(KEYA或KEYB)所对应的Sector内的应用块Block0,1,2进行数据读/写/更新等操作。 由于非接触式智能卡的操作,包括数据流的传递等都是以“非接触”方式来完成的,因此在MCU与非接触式智能卡之间必须有一个传递密码(或数据流)的中间媒体,即ASIC模块。RC150/170就是这样一种ASIC模块。它担负着非接触式智能卡与MCU(微处理机)之间所有的密码/数据相互传递的重要任务。对非接触式智能卡进行密码操作,变成对RC150/170ASIC模块进行密码操作。RC150/170ASIC模块与非接触式智能卡之间的信息传递(包括密码等)对用户来说是透明的,会自动传递并完成。因此如何对非接触式智能卡进行“密码操作”(对Block3的操作)变成如何对RC150/170ASIC模块进行密码操作。Philips公司的MCM200模块,MCM500模块或SB201,SB601(Uni-VisionEngineeringLtd.的产品)模块中都包含有RC150/170ASIC模块,因此本文所讨论的内容,包括下面设计的程序等,也适用于这些模块。RC170是RC150的新一代ASIC模块,速度较快。 现在我们广泛使用的非接触式智能卡读写设备中大都包含有以上所列的ASIC模块之一。 图1显示了在用户(MCU)与非接触式智能卡之间基本的密码传输关系,并请特别注意ASIC模块RC150/170的作用等等。
图1ASIC模块密码传输关系图 在研究ASIC模块RC150/170的时候,我们必须关注所有与“密码操作”有关的寄存器/存储器的情况。 ●密码数据寄存器KeyDataRegister(寄存器地址:0x0A); ●密码地址寄存器KeyAddressRegister(寄存器地址:0x0C); ●密码状态/控制寄存器KeyStatus&ControlRegister(KEYSTACON)(寄存器地址:0x0B); ●其他相关寄存器。 所有这些与“密码操作”相关的寄存器都是“只可写不可读”的,即WOM(Write-Only-Memory)。因此不要试图去读取这些寄存器的内容。
3、“密码操作”的研究及其应用程序开发 通常,对非接触式智能卡的“密码操作”有两个主要步骤。每一个主要步骤又有若干个小的步骤有序并且必须是连续地完成。 “密码操作”的两个主要步骤是: ●“LOAD_KEY”密码存取 ●“AUTHENTICATION”密码认证
3.1“LOAD_KEY”密码存取 “LOAD_KEY”密码存取必须由以下步骤有序并连续地完成: ●设置新的密码值 ●设置密码状态/控制寄存器KeyStatus&ControlRegister(KEYSTACON) ●设置密码地址寄存器KeyAddressRegister(寄存器地址:0x0C) ●设置密码数据寄存器KeyDataRegister(寄存器地址:0x0A) ●校验STACON寄存器,以确定这次的“LOAD_KEY”密码存取是否有效 以下将按照上述的次序进行具体的程序设计,所有的程序都使用标准的Intel-51MCU指令,以利于读者在LOW-LEVEL级上移植到其相应的应用项目中。
3.1.1设置新的密码值 新的密码值为6个bytes,在如下的程序设计中被依次存放在MCU内部RAM的72H~77H的6个单元中;程序员亦可自定义其他的存储单元作为新的密码值存放的缓冲区;R1寄存器为新密码缓存首地址指针。如下所设置新的密码值为:“AAAAAAAAAAAA” SETUP_NEW_KEY_VALUE: ;MOV R7,#06H;密码长度为6bytes MOV R1,#72H;R1为新密码缓存首地址指针 MOV @R1,#0AAH;设置新密码值 MOV 73H,#0AAH MOV 74H,#0AAH MOV 75H,#0AAH MOV 76H,#0AAH MOV 77H,#0AAH 良好的经验告诉我们,为了确保整个智能卡系统的高度安全保密,我们有必要在程序设计中,在完成了“密码操作”之后,立即清除存放新的密码值的缓冲区,简单的方法如下: CLEAR_NEW_KEY_BUFFER: MOV R7,#06H;密码长度为6bytes MOV R1,#72H;R1为新密码缓存首地址指针 CLEAR_LOOP: MOV @R1,#00H;清除新密码值所在缓冲区 INC R1 DJNZ R7,CLEAR_LOOP
3.1.2设置密码状态/控制寄存器KeyStatus&ControlRegister(KEYSTACON) KEYSTACON寄存器是一个只可读不可写的寄存器(存储器),它指示出“密码操作”时所处的状态和要控制的ASIC内部“密码存储器RAM”的选择。这里所指的“状态”是指本次“密码操作”两个主要步骤中的一个。 KEYSTACON寄存器是一个8-bit的存储器,其中有用的位(bit)只有3位。其具体内容为:
其中,MSB(“A/L”位)若被设置为“0”,则意味着当前“密码操作”的“状态”是“LOAD_KEY(密码存取)”;若被设置为“1”,则当前“密码操作”的“状态”是“AUTHENTICATION(密码认证)”。 最后 2个bit:KS0KS1是密码集keyset的选择。在ASIC中共有3套密码集(keyset)和一个传输密码(TransportKey)可被选择。设置KS0、KS1的值实际上是在选择(寻址)ASIC模块内部存放密码的不同的存储器单元(密码箱)。如果“LOAD_KEY”(密码存取)时使用了keyset0,则“AUTHENTICATION”(密码认证)时只能使用keyset0,而不能使用keyset1或keyset2或其他,因为在ASIC模块内,keyset0指定的密码存储器地址单元与keyset1或keyset2所指定的密码存储器地址单元是不同的单元。这就好比去超级市场购物,入超市前您把您的包裹寄存在超市门前包裹箱A中,并得到打印有开起包裹箱A的(开箱)密码纸条;当您欲取回包裹时,拿着包裹箱A的(开箱)密码纸条而去开包裹箱B或C的箱门,当然不能打开,因为您的地址(箱号)不对,当然您的包裹也不能拿到。这是密码的认证出错。在ASIC中有相同之处。如果“LOAD_KEY”(密码存取)时使用了keyset0,并存放上密码,而在“AUTHENTICATION”(密码认证)时却使用keyset1或keyset2或其他而来验证刚才存放的密码,当然会得到ASIC模块返回的认证出错(“AE=1”)。 当KS1KS0=“00”时,选择使用keyset0; 当KS1KS0=“01”时,选择使用keyset1; 当KS1KS0=“10”时,选择使用keyset2; 当KS1KS0=“11”时,选择使用传输密码(TransportKey)。 以下是设置密码状态/控制寄存器KeyStatus&ControlRegister(KEYSTACON)的程序: SETUP_KEYSTACON: MOV 7EH,#00000000B;选择使用keyset0,并指明是“LOAD_KEY” MOV A,7EH ;7EH单元存放了设置KEYSTACON的值 MOV R0,#0BH ;KEYSTACON寄存器地址为0Bh OVX @R0,A ;设置KEYSTACON寄存器 如果我们要选择使用keyset2,则相应可以设置7EH单元为#00000010b(0x02),即: MOV 7EH,#00000010B
3.1.3设置密码地址寄存器KeyAddressRegister(寄存器地址:0x0C) 在成功地完成了对密码状态/控制寄存器(KEYSTACON)的设置之后,必须立即对密码地址寄存器KeyAddressRegister进行设置,而不能对密码数据寄存器KeyDataRegister进行设置或做其他设置,否则将出错。因为ASIC内部接收MCU指令/数据的存储单元是按照FIFO(“FirstInFirstOut”即“先进先出”)方式工作的。 由于一张非接触式智能卡有16个Sector(扇区),并且每个Sector都可能有着各自不同的密码,因此在ASIC模块中就会有不同的密码存储器与之相对应。当对16个Sector中的一个Sector进行密码操作时,就必须对ASIC模块中与该Sector对应的密码存储器进行寻址,找到这一密码存储器确切位置。不过,MCU送出的寻址地址只是ASIC在其内部做第二次寻址(地址变化)的“一部分”地址。这里所指的“一部分”是出于高度安全保密的原因。 以下是8位(bit)密码地址寄存器的说明:
这里, ●MSB(“A/L”bit)与KEYSTACON寄存器中的MSB有着相同的意义; ●“A/B”bit位指出MCU要使用的密码的类型。当“A/B”=“0”时,MCU使用KEYA;当“A/B”=“1”时,MCU使用KEYB; ●“A5~A0”指出要求密码操作的某一Sector的地址。当要对Sector0进行密码操作时,“A5~A0”应该被设置为“00000b”(0x00);如果是Sector1,“A5~A0”应该被设置为“00001b”(0x01);如果是Sector5,“A5~A0”应该被设置为“00101b(0x05),等等。 以下是设置密码地址寄存器KeyAddressRegister的程序: SETUP_Key_Address_Reg: MOV 7DH,#00000001B ;使用KEYA,对Sector1进行“LOAD_KEY” MOV A,7DH ;7DH单元存储了密码地址寄存器值 MOV R0,#0CH ;密码地址寄存器地址为“0Ch” MOV X@R0,A ;设置密码地址寄存器 如果要对Sector1使用KEYB,则7DH单元必须设置为“#01000001b”(0x41),即: MOV 7DH,#01000001B 更进一步,如果要对Sector5使用KEYB,则7DH单元必须设置为“#01000101b”(0x45),即: V 7DH,#01000101B 这样,Sector5中Block0,1,2(相应于绝对块地址为:Block20,21,22)中原有数据将可以被操作。Sector5中Block3也可以按照预先定义的存取控制条件而被改写密码,或被读出密码或控制字节。
3.1.4设置密码数据寄存器KeyDataRegister(寄存器地址:0x0A) 如果成功地完成了以上几个方面的设置,ASIC模块现在可以接收MCU送出的新的密码值了,即,现在应该设置密码数据寄存器KeyDataRegister。 密码数据寄存器KeyDataRegister也是WOM类型的存储器。只可写入数据,不可读出数据,或读到的数据是无效的。由于密码的长度为6bytes,因此密码数据寄存器KeyDataRegister也将由6个bytes的FIFO存储器组成。 以下是设置密码数据寄存器KeyDataRegister的程序: SETUP_Key_Data_Reg: MOV R1,#72H ;R1为新密码缓存(72H~77H)首地址指针 MOV R7,#06H ;密码长度=6bytes MOV R0,#0AH ;密码数据寄存器地址为:“0Ah” WRITE_Key_Data_Reg_LOOP: MOV A,@R1 ;取出一个byte的新密码值 MOV X@R0,A ;将一个byte的新密码值送入密码数据寄 ;存器中(ASIC模块中) INC R1 DJNZ R7,WRITE_Key_Data_Reg_LOOP 这里有一个非常重要的问题,即传送6bytes长度的密码时,这6bytes的顺序必须引起高度重视。 由于每一个Block3都有着如下的存储格式存放着密码KEYA,KEYB及4个字节的存取控制条件:
因此,密码数据寄存器接收MCU发送的第一个密码字节(byte)必须是KEYA中的第一个字节,即表中的“A0”字节。否则送入非接触式智能卡中的密码将是反向的6个字节。 密码KEYB具有相同之处。 3.1.5校验STACON寄存器,以确定这次的“LOAD_KEY”(密码存取)是否有效 在完成上述操作后,接着应该对以上的结果进行校验,以确定这次的“LOAD_KEY”(密码存取)是否有效。这可以通过校验STACON寄存器中的“AE”bit位来完成。 STACON寄存器是ASIC模块中极为重要的状态寄存器和控制寄存器。 当对ASIC模块进行任何读/写操作时,它是一个状态寄存器,指出当时读/写操作的状态是如何的。此时的STACON寄存器有着如下的8个bit的状态格式:
当对ASIC模块进行任何控制操作时,它是一个控制寄存器,此时的STACON寄存器又有着如下的8个bit的控制格式:
我们进行密码操作,读写ASIC模块时,只是会涉及STACON寄存器中的“AuthenticationError”bit(即“AE”位)。 ●当“AE”=“1”时,指明刚才的密码操作(“LOAD_KEY”或“AUTHENTICATION”)没有成功; ●当“AE”=“0”时,指明刚才的密码操作(“LOAD_KEY”或“AUTHENTICATION”)成功; 以下是校验STACON寄存器,以确定这次“LOAD_KEY”密码存取操作是否有效的校验程序: VERIFY_LOAD_KEY_Operationroutine: VERIFY_LOAD_KEY_OP: MOV R0,#01H ;STACON寄存器地址为“01H” MOV XA,@R0 ;读ASIC内的STACON寄存器;如果“AE”=“1”,转出错处理 JB ACC.2, LOAD_KEY_Operation_ERR ;否则“AE”=“00”,此次“LOAD_KEY”成功 MOV B,#00H;送OK标志“00” AJMP LOAD_KEY_Operation_OK LOAD_KEY_Operation_ERR: MOV B,#99H;送出错标志“99”,此次“LOAD_KEY”失败 ...... (出错处理) ...... AJMP VERIFY_EXIT LOAD_KEY_Operation_OK: MOV A,B ACALL DISPLAY ...... (“OK”处理) ...... VERIFY_EXIT: RET
3.2“AUTHENTICATION”(密码认证) “AUTHENTICATION”(密码认证)操作必须按照如下的几个步骤进行: ●设置ASIC模块中的TOC/BCNTS寄存器等 ●设置密码状态/控制寄存器KeyStatus&ControlRegister(KEYSTACON) ●设置密码地址寄存器KeyAddressRegister(寄存器地址:0x0C) ●设置AUTHENTICATION指令码 ●密码地址变换 ●校验STACON寄存器,以确定这次的“AUTHENTICATION”密码认证是否有效 ●关闭TOC及一些其它操作等 由于“AUTHENTICATION”(密码认证)操作同“LOAD_KEY”(密码存取)操作相互类似,在此不再重复。 只有在完全完成了上述的两个主要的密码操作步骤,并且得当了ASIC模块“OK”的响应,非接触式智能卡上相对应与刚才进行过密码操作的某一扇区Sectorm内的Block0,1,2才能被MCU进行访问,包括进行读/写等数据操作。一旦要求对另一扇区Sectorn内的Block进行数据读写时,则必须重新开始对扇区Sectorn进行密码操作,包括“LOAD_KEY”(密码存取)操作和“AUTHENTICATION”(密码认证)操作等。
4、结束语 非接触式智能卡技术虽然至今只有4~5年的成熟发展期,但是由于它的高度保密性,以及使用的方便性,得到了很快的普及。这种普及又加速了非接触式智能卡技术的飞跃发展。它同银行用接触式CPU卡相互融合,产生了新的双界面智能卡(Contact&ContactlessInterface),在e-purse电子钱包系统等方面取得到了很大的成功。世界上一些著名的大公司,如SONY公司等,也介入了非接触式智能卡技术领域,并且SONY的非接触式智能卡技术又有着非常独到之处。根据笔者对SONY非接触式智能卡技术的使用、研究和了解,相对MIFARE而言,其在读卡的速度、稳定性、误码率等性能上都有很大的提高,这也是其溶入了新的技术所致。
|