|  | 
          1樓
          巨大八爪鱼
          2017-2-22 08:12
          
          
            /* ORG悬空,选16位模式 */#include <at89x52.h>
 
 #define _BV(n) (1 << (n))
 
 sbit CS = P1^0;
 sbit SK = P1^1;
 sbit DI = P1^2;
 sbit DO = P1^3;
 
 unsigned char code seg8[] = {0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90};
 unsigned int num = 0;
 
 void delay(unsigned int n)
 {
 unsigned char i;
 while (n--)
 for (i = 0; i < 115; i++);
 }
 
 // 在数码管上显示num的值
 void seg_scan(void)
 {
 char i;
 unsigned int n = num;
 for (i = 7; i >= 3; i--) // 从低位扫描到高位
 {
 P2 = 0xff;
 P0 = seg8[n % 10];
 P2 = ~_BV(i);
 delay(3);
 n /= 10;
 }
 }
 
 void _93C46_WriteOP(unsigned char op)
 {
 // 初态
 CS = 0;
 SK = 0;
 DI = 1;
 
 // 开始位
 CS = 1;
 SK = 1;
 SK = 0;
 
 // OP位
 if ((op & 2) == 0)
 DI = 0;
 SK = 1;
 SK = 0;
 if (op & 1)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 }
 
 void _93C46_WriteAddress(unsigned char addr)
 {
 unsigned char i;
 for (i = 0; i < 6; i++)
 {
 if (addr & 0x20)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 addr <<= 1;
 }
 DI = 0;
 }
 
 unsigned int _93C46_ReadWord(void)
 {
 unsigned char i;
 unsigned int dat = 0;
 DO = 1;
 for (i = 0; i < 16; i++)
 {
 SK = 1;
 dat <<= 1;
 if (DO)
 dat |= 1;
 SK = 0;
 }
 return dat;
 }
 
 unsigned int _93C46_Read(unsigned char addr)
 {
 unsigned int dat;
 _93C46_WriteOP(2);
 _93C46_WriteAddress(addr);
 dat = _93C46_ReadWord();
 CS = 0;
 return dat;
 }
 
 void _93C46_WriteWord(unsigned int dat)
 {
 unsigned char i;
 for (i = 0; i < 16; i++)
 {
 if (dat & 0x8000)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 dat <<= 1;
 }
 DI = 0;
 }
 
 // 等待操作完毕
 void _93C46_Wait(void)
 {
 CS = 0;
 CS = 1;
 DO = 1; // tSV<=250ns
 while (!DO);
 CS = 0;
 }
 
 // 允许/禁止擦写
 void _93C46_EnableWrite(unsigned char enabled)
 {
 _93C46_WriteOP(0);
 _93C46_WriteAddress((enabled) ? 0x30 : 0x00);
 CS = 0;
 }
 
 // 写入单个存储单元
 void _93C46_Write(unsigned char addr, unsigned int dat)
 {
 _93C46_WriteOP(1);
 _93C46_WriteAddress(addr);
 _93C46_WriteWord(dat);
 _93C46_Wait();
 }
 
 // 擦除单个存储单元
 void _93C46_Erase(unsigned char addr)
 {
 _93C46_WriteOP(3);
 _93C46_WriteAddress(addr);
 _93C46_Wait();
 }
 
 // 擦除所有存储单元(设为0xffff)
 void _93C46_EraseAll(void)
 {
 _93C46_WriteOP(0);
 _93C46_WriteAddress(0x20);
 _93C46_Wait();
 }
 
 // 将所有的存储单元设为指定值
 void _93C46_WriteAll(unsigned int dat)
 {
 _93C46_WriteOP(0);
 _93C46_WriteAddress(0x10);
 _93C46_WriteWord(dat);
 _93C46_Wait();
 }
 
 int main(void)
 {
 _93C46_EnableWrite(1); // 允许写入
 num = _93C46_Read(10);
 _93C46_Write(10, num + 1);
 
 _93C46_EnableWrite(0); // 禁止写入
 _93C46_WriteAll(78);
 _93C46_Erase(10);
 _93C46_EraseAll();
 
 while (1)
 seg_scan();
 }
 
 | 
    
      |  | 
          2樓
          巨大八爪鱼
          2017-2-22 08:45
          
          
            【一次性读多个存储单元】/* ORG悬空,选16位模式 */
 #include <at89x52.h>
 
 #define _BV(n) (1 << (n))
 
 sbit CS = P1^0;
 sbit SK = P1^1;
 sbit DI = P1^2;
 sbit DO = P1^3;
 
 unsigned char code seg8[] = {0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90, 0x88, 0x83, 0xa7, 0xa1, 0x86, 0x8e};
 struct datablock
 {
 unsigned int id;
 unsigned int num;
 } db;
 
 void delay(unsigned int n)
 {
 unsigned char i;
 while (n--)
 for (i = 0; i < 115; i++);
 }
 
 void seg_scan(void)
 {
 char i;
 unsigned int n = db.id;
 for (i = 3; i >= 0; i--)
 {
 P2 = 0xff;
 P0 = seg8[n & 0x0f];
 P2 = ~_BV(i);
 delay(2);
 n >>= 4;
 }
 
 n = db.num;
 for (i = 7; i >= 4; i--)
 {
 P2 = 0xff;
 P0 = seg8[n & 0x0f];
 P2 = ~_BV(i);
 delay(2);
 n >>= 4;
 }
 }
 
 void _93C46_WriteOP(unsigned char op)
 {
 // 初态
 CS = 0;
 SK = 0;
 DI = 1;
 
 // 开始位
 CS = 1;
 SK = 1;
 SK = 0;
 
 // OP位
 if ((op & 2) == 0)
 DI = 0;
 SK = 1;
 SK = 0;
 if (op & 1)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 }
 
 void _93C46_WriteAddress(unsigned char addr)
 {
 unsigned char i;
 for (i = 0; i < 6; i++)
 {
 if (addr & 0x20)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 addr <<= 1;
 }
 DI = 0;
 }
 
 unsigned int _93C46_ReadWord(void)
 {
 unsigned char i;
 unsigned int dat = 0;
 DO = 1;
 for (i = 0; i < 16; i++)
 {
 SK = 1;
 dat <<= 1;
 if (DO)
 dat |= 1;
 SK = 0;
 }
 return dat;
 }
 
 // 读入多个存储单元
 void _93C46_ReadBlock(unsigned char addr, unsigned int *dat, unsigned char count)
 {
 _93C46_WriteOP(2);
 _93C46_WriteAddress(addr);
 while (count > 0)
 {
 *dat++ = _93C46_ReadWord();
 count -= 2;
 }
 CS = 0;
 }
 
 int main(void)
 {
 _93C46_ReadBlock(0, (unsigned int *)&db, sizeof(db));
 while (1)
 seg_scan();
 }
 
 | 
    
      |  | 
          3樓
          巨大八爪鱼
          2017-2-22 13:45
          
          
            void _93C46_EnableWrite(unsigned char enabled)这里enabled参数用bit类型更好一点。
 
 | 
    
      |  | 
          4樓
          巨大八爪鱼
          2017-2-23 18:44
          
          
            【全部存储单元测试】/* ORG悬空,选16位模式 */
 #include <at89x52.h>
 
 #define _BV(n) (1 << (n))
 
 sbit CS = P1^0;
 sbit SK = P1^1;
 sbit DI = P1^2;
 sbit DO = P1^3;
 
 unsigned char code seg8[] = {0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90, 0x88, 0x83, 0xa7, 0xa1, 0x86, 0x8e};
 unsigned char id;
 unsigned int num;
 
 void delay(unsigned int n)
 {
 unsigned char i;
 while (n--)
 for (i = 0; i < 115; i++);
 }
 
 void seg_scan(void)
 {
 char i;
 unsigned int n = id;
 for (i = 1; i >= 0; i--)
 {
 P2 = 0xff;
 P0 = seg8[n % 10];
 P2 = ~_BV(i);
 delay(2);
 n /= 10;
 }
 
 n = num;
 for (i = 7; i >= 3; i--)
 {
 P2 = 0xff;
 P0 = seg8[n % 10];
 P2 = ~_BV(i);
 delay(2);
 n /= 10;
 }
 }
 
 void _93C46_WriteOP(unsigned char op)
 {
 // 初态
 CS = 0;
 SK = 0;
 DI = 1;
 
 // 开始位
 CS = 1;
 SK = 1;
 SK = 0;
 
 // OP位
 if ((op & 2) == 0)
 DI = 0;
 SK = 1;
 SK = 0;
 if (op & 1)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 }
 
 void _93C46_WriteAddress(unsigned char addr)
 {
 unsigned char i;
 for (i = 0; i < 6; i++)
 {
 if (addr & 0x20)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 addr <<= 1;
 }
 DI = 0;
 }
 
 unsigned int _93C46_ReadWord(void)
 {
 unsigned char i;
 unsigned int dat = 0;
 DO = 1;
 for (i = 0; i < 16; i++)
 {
 SK = 1;
 dat <<= 1;
 if (DO)
 dat |= 1;
 SK = 0;
 }
 return dat;
 }
 
 unsigned int _93C46_Read(unsigned char addr)
 {
 unsigned int dat;
 _93C46_WriteOP(2);
 _93C46_WriteAddress(addr);
 dat = _93C46_ReadWord();
 CS = 0;
 return dat;
 }
 
 void _93C46_WriteWord(unsigned int dat)
 {
 unsigned char i;
 for (i = 0; i < 16; i++)
 {
 if (dat & 0x8000)
 DI = 1;
 else
 DI = 0;
 SK = 1;
 SK = 0;
 dat <<= 1;
 }
 DI = 0;
 }
 
 // 等待操作完毕
 void _93C46_Wait(void)
 {
 CS = 0;
 CS = 1;
 DO = 1; // tSV<=250ns
 while (!DO);
 CS = 0;
 }
 
 // 允许/禁止擦写
 void _93C46_EnableWrite(unsigned char enabled)
 {
 _93C46_WriteOP(0);
 _93C46_WriteAddress((enabled) ? 0x30 : 0x00);
 CS = 0;
 }
 
 // 写入单个存储单元
 void _93C46_Write(unsigned char addr, unsigned int dat)
 {
 _93C46_WriteOP(1);
 _93C46_WriteAddress(addr);
 _93C46_WriteWord(dat);
 _93C46_Wait();
 }
 
 int main(void)
 {
 unsigned char i;
 
 _93C46_EnableWrite(1);
 for (i = 0; i < 64; i++)
 _93C46_Write(i, 10000 + i * 100 + i);
 _93C46_EnableWrite(0);
 
 while (1)
 {
 num = _93C46_Read(id);
 for (i = 0; i < 50; i++)
 seg_scan();
 
 id++;
 if (id > 63)
 id = 0;
 }
 }
 
 |