📄 ic.c
字号:
//***********IC卡引脚信号处理***************//
void RST(unsigned char PD) //RST=PE^2
{if(PD==1) PORTE|=0x04;//RST置1
else PORTE&=~0x04;//RST置0
}
void CLK(unsigned char PD) //CLK=PE^1
{
if(PD==1) PORTE|=0x02;//CLK置1
else PORTE&=~0x02;//CLK置0
}
void IO(unsigned char PD) //IO=PE^0
{
if(PD==1) PORTE|=0x01;//IO置1
else PORTE&=~0x01;//IO置0
}
void SetIO(unsigned char i)//设置IO口属性
{if(i==1) DDRE|=0x01; //IO口输出:1111 0000带上拉输出
else DDRE&=~0x01; //IO口输如:1110 0000 不带上拉输入
PORTE&=~0x01;//不带上拉电阻;
}
//**********延时函数(Us数量级)*********//
void DelayUs(unsigned int time)
{
do
time--;
while(time>1);
}
//****************延时函数(Ms数量级)**//
void DelayMs(unsigned int time)
{
while(time!=0)
{
DelayUs(1000);
time--;
}
}
//****************接收数据**************//
unsigned char ReceiveData(void)
{unsigned char count;
unsigned char value;
unsigned char io_value;
value=0;
SetIO(0);//设置IO脚为输入;
CLK(0);
for(count=0;count<8;count++)
{value=value>>1;
io_value=PINE;
if(io_value&0x01) value|=0x80;//判断IO脚是否为1
else value&=0x7f;
CLK(1);
DelayUs(10);
CLK(0);
DelayUs(10);
}
return (value);
}
//****************复位**************//
void ResetIC(void)
{uchar count;
SetIO(1); //设置IC卡引脚的属性 ,indata
//DelayUs(70);
RST(1);
DelayUs(10);
CLK(1);
DelayUs(20);
CLK(0);
DelayUs(10);
RST(0);
DelayUs(10);
count=ReceiveData();
count=ReceiveData();
count=ReceiveData();
count=ReceiveData();
}
//********************发送数据************//
void SendData(unsigned char Xdata)
{unsigned char count;
unsigned char value;
unsigned char i;
SetIO(1);////设置IO脚为输出;
for(count=8;count>0;count--)
{
value=Xdata;
i=value<<(count-1);
if(i&0x80) IO(1); //发送先发低位,后发高位
else IO(0);
CLK(1);
DelayUs(10);
CLK(0);
DelayUs(10);
}
}
void power_on(void)
{
//unsigned char count;
SetIO(0); //设置IC卡引脚的属性 ,indata
DelayUs(70);
RST(1);
DelayUs(10);
CLK(1);
DelayUs(30);
CLK(0);
DelayUs(10);
RST(0);
DelayUs(10);
CLK(1);
DelayUs(30);
CLK(0);
DelayUs(10);
//for(count=4;count>0;count--)
// {*Xdata=ReceiveData();
// Xdata+=1;}
}
//*******************Start条件****************//
void Start(void)
{SetIO(1);
IO(1);
CLK(1);
DelayUs(10);
IO(0);
DelayUs(10);
CLK(0);
}
//*******************Stop条件****************//
void Stop(void)
{
SetIO(1);
CLK(1);
IO(0);
DelayUs(10);
IO(1);
DelayUs(10);
}
//******************处理过程**************//
void Process(void)
{uint j,k;
SetIO(1);//设置IO脚为输出脚
CLK(0);
DelayUs(10);
IO(0);
for(j=250;j>0;j--)
{
IO(0);
CLK(1);
DelayUs(10);
CLK(0);
DelayUs(10);
}
}
//****************说明*********************//
//*********输出模式接口命令,包括读主存储器30H,读保护存储器34H,读安全代码的接口命令31H***********//
//******处理模式数据接口命令,包括写主存储器38H,写保护存储器3CH,写安全代码39H,校验安全代码33H*******//
void Command(unsigned char Byte1,unsigned char Byte2,unsigned char Byte3)
{Start();
SendData(Byte1);
SendData(Byte2);
SendData(Byte3);
Stop();
}
/**********读主存储器**************/
void ReadMainMemory(unsigned char addr,unsigned char *p,unsigned char N)
{Command(0x30,addr,0xff);
do{*p=ReceiveData();
p++;}while(N--);
ResetIC();
}
/************写主存储器************/
void WriteMainMemory(unsigned char Address,unsigned char *tt)
{Command(0x38,Address,*tt);
Process();
}
/**************读安全存储器************/
void ReadSafeMemory(unsigned char *p)
{unsigned char i;
Command(0x31,0xff,0xff);
for(i=0;i<4;i++)
{*p=ReceiveData();
p++;}
ResetIC();
}
/*************写安全存储器***************/
void WriteSafeMemory(unsigned char Address,unsigned char tt)
{Command(0x39,Address,tt);//Address=0,1,2,3
Process();
}
/**************校验密码*******************/
unsigned char VerifyPassword(unsigned char *p)
{unsigned char temp[4]={0,0,0,0};//暂存4字节保护密码;
unsigned char i;
ResetIC();
ReadSafeMemory(temp);//读安全代码以取得错误计数器
if((temp[0]&0x07)!=0)
{
if((temp[0]&0x07)==0x07) i=0x06;
else if((temp[0]&0x07)==0x06) i=0x04;
else if((temp[0]&0x07)==0x04) {i=0x00;return (0);}
WriteSafeMemory(0,i);
for(i=1;i<4;i++,p++)
{
Command(0x33,i,*p);
Process();
}
WriteSafeMemory(0,0xff);
ReadSafeMemory(temp);
if((temp[0]&0x07)==0x07)
return(1);
}//if((temp[0]&0x07)!=0)
return(0);
}
/*************检测是否有卡************************/
unsigned char IC_power(void)
{
DDRE&=~0X08; //PE3
if((PINE&0X08)==0X00)
{
DelayMs(100);
if((PINE&0X08)==0X00)
return(1);
else
return(0);
}
else
return(0);
}
/*****************************解锁写入
************************************************************/
void write_IC(unsigned char i)
{
EEPROM_write(0x50,i);
}
/*****************************解锁读取 EEPROM地址:0x50
************************************************************/
void read_IC(void)
{
IC_chok=EEPROM_read(0x50);
if((IC_chok!=0x55)&&(IC_chok!=0xaa))//容错
{
IC_chok=0x55;
write_IC(0x55);
}
}
/*****************************区位密码读取 EEPROM地址:0x53
0x54
************************************************************/
unsigned int read_area(void)
{
unsigned int temp=0;
temp=EEPROM_read(0x53);
temp=temp+(EEPROM_read(0x54)<<8);
return (temp);
}
/*****************************区位密码写入
************************************************************/
void write_area(unsigned int ii)
{
unsigned char temp;
temp=(unsigned char)(ii);
EEPROM_write(0x53,temp);
temp=(unsigned char)(ii>>8);
EEPROM_write(0x54,temp);
}
/*******************************************/
//ic卡天数信息读出 地址为32/33,,一样的数
/*******************************************/
uchar IC_day_read(void)
{
unsigned char *pp;
unsigned char temp1[2]={0,0};
pp=&temp1[0];
ReadMainMemory(32,pp,2);
return (temp1[0]);
}
/*******************************************/
//ic卡天数信息写入
/*******************************************/
void IC_day_write(uchar DATA)
{
unsigned char temp0[2]={0,0};
unsigned char *aa;
unsigned char ii=0;
temp0[0]=DATA;
temp0[1]=DATA;
aa=&temp0[0];
for(ii=0;ii<2;ii++,aa++)
{
WriteMainMemory(32+ii,aa);
}
}
/****************读出IC卡信息(金额或区域码)***************/
unsigned int IC_information(unsigned char ADDress)
{
unsigned int temp;
unsigned char *pp;
unsigned char temp1[2]={0,0};
pp=&temp1[0];
ReadMainMemory(ADDress,pp,2);
temp=(unsigned int)(temp1[1]+(temp1[0]<<8));
return (temp);
}
/****************写入IC卡信息(金额)***********************/
void WR_IC_information(unsigned int Information,unsigned char Address)
{
unsigned char *aa;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -