Merge branch 'hotfix/1.0.8'
diff --git a/.sign_salt b/.sign_salt
new file mode 100644
index 0000000..47e24b0
--- /dev/null
+++ b/.sign_salt
@@ -0,0 +1 @@
+nzoqPYMIu91VViA/mEIG5FtJXi8=
\ No newline at end of file
diff --git a/Makefile b/Makefile
index ea4310f..a2b9653 100644
--- a/Makefile
+++ b/Makefile
@@ -1,6 +1,11 @@
-TARGET=g40130x
+TARGET=g401201
 UV4=/C/Keil/UV4/Uv4.exe
 
+SALT_KEY=.sign_salt
+
+SIGN_201=./g401302/outFlow/G401302_flow.bin
+SIGN201_FILE=./g401302/outFlow/G401302.sign
+
 .PHONY: clean all
 
 timer: clean
@@ -11,6 +16,10 @@
 	@echo "build shu version ..."
 	$(UV4) -cr -j0 -b g401302/project/g401302.uvproj -t"flow" -o"outFlow/OUTPUTFILE.TXT"
 	
+sign:
+	@echo "calc upgrade file sign ..."
+	cat $(SIGN_201) $(SALT_KEY) | sha256sum - | cut -d' ' -f 1 | tr -d '\n' > $(SIGN201_FILE)
+	
 all: timer flow
 
 clean:
diff --git a/supwisdom/sp_card.c b/supwisdom/sp_card.c
index 4fcbd65..e23cd61 100644
--- a/supwisdom/sp_card.c
+++ b/supwisdom/sp_card.c
@@ -122,9 +122,8 @@
   {
     return ret;
   }
-  offset = 0;
-  MEMCLEAR(card->citizen_cardno, sizeof(card->citizen_cardno));
-  offset += 31;
+  offset = 31;
+  offset += 8;
   MEMCPY(card->citizen_cardno, buff+offset, sizeof(card->citizen_cardno));
   offset += 12;
   offset += 18;
diff --git a/supwisdom/sp_communicate.c b/supwisdom/sp_communicate.c
index 79b5601..3ea33cf 100644
--- a/supwisdom/sp_communicate.c
+++ b/supwisdom/sp_communicate.c
@@ -36,6 +36,8 @@
   uint8 temp[sizeof(sp_protocol_response_t)];
   tick = sp_get_ticker();
   MEMCLEAR(temp,sizeof temp);
+  memset(pos->errmsg,0,32);
+  pos->errmsglen = 0;
   while(1)
   {
 
@@ -57,6 +59,11 @@
           if(MEMCMP((uint8*)resp +datalen,crc,2) == 0)
           {
             MEMCLEAR(&(pos->last_comm_status), sizeof(sp_comm_status_t));
+            if(resp->retcode)
+            {
+              MEMCPY(pos->errmsg,resp->data,32);
+              pos->errmsglen = resp->datalen;
+            }
             return resp->retcode;
           }
         }
@@ -137,7 +144,7 @@
     }
     else if(IS_KEY(PK_INT_AMOUNT_LIMIT,field.key))
     {
-      card->amountlimit = (uint32)field.val.intval;
+      card->amountlimit = (uint32)field.val.intval*10;
     }
   }
   //disp_hint_info(pos,"Éí·ÝÈÏÖ¤³É¹¦",DELAY_TIME1s);
@@ -160,7 +167,7 @@
   cw_pack_map_size(&pack,4);
 
   sp_pack_put_bin(&pack, PK_BIN_CARDPHYID, card->cardphyid, 4);
-  sp_pack_put_bin(&pack, PK_BIN_CITIZEN_CARDNO, card->citizen_cardno+8, 4);
+  sp_pack_put_bin(&pack, PK_BIN_CITIZEN_CARDNO, card->citizen_cardno, 4);
   sp_pack_put_bin(&pack, PK_BIN_DEVPHYID, pos->devphyid, 4);
   sp_pack_put_bin(&pack, PK_BIN_DEVTIME, ctime, 6);
 
@@ -353,7 +360,7 @@
     }
     else if(IS_KEY(PK_INT_PAYAMT, field.key))
     {
-      card->qrcode.paidAmount = (uint8)field.val.intval;
+      card->qrcode.paidAmount = (uint32)field.val.intval;
     }
     else if(IS_KEY(PK_INT_FEEAMOUNT,field.key))
     {
@@ -377,7 +384,7 @@
     }
     else if(IS_KEY(PK_INT_AMOUNT_LIMIT,field.key))
     {
-      card->amountlimit = (uint16)field.val.intval;
+      card->amountlimit = (uint32)field.val.intval*10;
     }
   }
   return resp.retcode;
@@ -410,10 +417,12 @@
   cw_pack_context pack;
   sp_protocol_request_t req;
 
+  pos->heartbeat.heart_status = HEART_SEND;
+
   transdtl_account_cobilLno = transdtl->cobillno;
   sp_protocol_req_init(&req, SP_CMD_TRANSDTL_ACCOUNT);
   sp_pack_init(&pack,req.data,sizeof(req.data));
-  cw_pack_map_size(&pack,10);
+  cw_pack_map_size(&pack,11);
 
   sp_pack_put_bin(&pack, PK_BIN_DEVPHYID, transdtl->devphyid,4);
   sp_pack_put_bin(&pack, PK_BIN_TRANSDATE, transdtl->transdate,3);
@@ -421,6 +430,7 @@
   sp_pack_put_int(&pack, PK_INT_COBILLNO, transdtl->cobillno);
   sp_pack_put_bin(&pack, PK_BIN_CARDPHYID, transdtl->cardphyid,
                   sizeof(transdtl->cardphyid));
+  sp_pack_put_bin(&pack, PK_BIN_CITIZEN_CARDNO, transdtl->cardno, 4);
   sp_pack_put_int(&pack, PK_INT_TRANSWAY, transdtl->transway);
   sp_pack_put_int(&pack, PK_INT_AMOUNT, transdtl->amount);
   sp_pack_put_int(&pack, PK_INT_PAYAMT, transdtl->paidAmount);
@@ -440,29 +450,30 @@
   cw_unpack_context unpack;
   unpack_field_t field;
 
-  if(!resp->retcode)
+  if(resp->retcode)
   {
-    sp_unpack_init(&unpack, resp->data, resp->datalen);
-    size = sp_unpack_map_size(&unpack);
-    while(size-- > 0)
+    return resp->retcode;
+  }
+  pos->heartbeat.heart_status = HEART_RECV;
+  sp_unpack_init(&unpack, resp->data, resp->datalen);
+  size = sp_unpack_map_size(&unpack);
+  while(size-- > 0)
+  {
+    sp_unpack_value(&unpack,&field);
+    if(IS_KEY(PK_INT_COBILLNO,field.key))
     {
-      sp_unpack_value(&unpack,&field);
-      if(IS_KEY(PK_INT_COBILLNO,field.key))
+      if(field.val.intval == transdtl_account_cobilLno)
       {
-        if(field.val.intval == transdtl_account_cobilLno)
+        pos->unconfirm_transdtl.transaddr+= sizeof(sp_transdtl_t);
+        if(ADDR_TRANSDTL_END <= pos->unconfirm_transdtl.transaddr)
         {
-          pos->unconfirm_transdtl.transaddr+= sizeof(sp_transdtl_t);
-          if(ADDR_TRANSDTL_END <= pos->unconfirm_transdtl.transaddr)
-          {
-            pos->unconfirm_transdtl.transaddr= ADDR_TRANSDTL_BEGIN;
-          }
-          return sp_write_unconfirm_record(pos);
+          pos->unconfirm_transdtl.transaddr= ADDR_TRANSDTL_BEGIN;
         }
+        return sp_write_unconfirm_record(pos);
       }
     }
   }
   return resp->retcode;
-
 }
 
 static uint8 sp_confirm_heartbeat(sp_protocol_response_t* resp, sp_pos_t* pos)
diff --git a/supwisdom/sp_config.h b/supwisdom/sp_config.h
index 3daed08..60065ad 100644
--- a/supwisdom/sp_config.h
+++ b/supwisdom/sp_config.h
@@ -103,13 +103,14 @@
   uint8 transtime[3];
   uint32 cobillno;		//½»Ò×¶©µ¥±àºÅ
   uint8 cardphyid[4];	//¿¨ÎïÀíid
+  uint8 cardno[4]; //ÊÐÃñ¿¨ºÅ
   uint8 transway;		//½»Ò×·½Ê½£¬0-³õʼ£¬1-Ë¢¿¨£¬2-ɨÂë
-  uint8 amount;			//ʵ¼ÊÖ§¸¶½ð¶î
-  uint8 paidAmount;		//ÒÑÖ§¸¶½ð¶î£¬µ±ÊÇÏȿ۷ÑģʽÏ£¬¼Ç¼ÒÑÖ§¸¶µÄ½ð¶î
-  uint8 flowsensors;	//ʵ¼ÊʹÓüÆÁ¿£¨µ¥Î»£º°ÙºÁÉý£©
+  uint32 amount;			//ʵ¼ÊÖ§¸¶½ð¶î
+  uint32 paidAmount;		//ÒÑÖ§¸¶½ð¶î£¬µ±ÊÇÏȿ۷ÑģʽÏ£¬¼Ç¼ÒÑÖ§¸¶µÄ½ð¶î
+  uint32 flowsensors;	//ʵ¼ÊʹÓüÆÁ¿£¨µ¥Î»£º°ÙºÁÉý£©
   uint8 transtatus;		//Á÷ˮ״̬£¬0-³õʼ£¬1-³É¹¦£¬2-ʧ°Ü
-  uint8 reverse[7];		//ռλ·û
-  uint8 crc[2]; 		//len=32
+  uint8 unused[26];		//ռλ·û
+  uint8 crc[2]; 		//len=64
 } sp_transdtl_t;
 
 typedef struct
@@ -144,12 +145,12 @@
 
   uint8 starttime[6];  	//Ë¢¿¨Ê±¼ä
   /*Ïȿۿîºó³öË®*/
-  uint16 prepaid_num;	//µ¥´Î¿ÉÓüÆÁ¿(µ¥Î»:100ml)
-  uint16 prepaid_amt;	//µ¥´ÎÔ¤¸¶½ðÇ®
+  uint32 prepaid_num;	//µ¥´Î¿ÉÓüÆÁ¿(µ¥Î»:100ml)
+  uint32 prepaid_amt;	//µ¥´ÎÔ¤¸¶½ðÇ®(µ¥Î»:Àå)
 
-  uint16 paid_num; 		//ÀۼƿÉÓüÆÁ¿(µ¥Î»:100ml)
-  uint16 paid_sum;  	//ÀÛ¼ÆÖ§¸¶½ð¶î
-  uint16 used_num; 		//ÒÑʹÓüÆÁ¿(µ¥Î»:100ml)
+  uint32 paid_num; 		//ÀۼƿÉÓüÆÁ¿(µ¥Î»:100ml)
+  uint32 paid_sum;  	//ÀÛ¼ÆÖ§¸¶½ð¶î(µ¥Î»:Àå)
+  uint32 used_num; 		//ÒÑʹÓüÆÁ¿(µ¥Î»:100ml)
 } sp_purchase_t;
 
 //¶þάÂëÐÅÏ¢
@@ -162,7 +163,7 @@
   uint32 waittime;		//³öË®µÈ´ýʱ¼ä
   uint8 authstatus;		//Óû§È·ÈÏ״̬£¨0-δȷÈÏ£¬1-ÒÑÈ·ÈÏ£©
   uint8 paystatus;		//Ö§¸¶×´Ì¬£¨0-´ýÖ§¸¶£¬ 1-ÒÑÖ§¸¶£¬ 2-´ú¿Û£¬3 - ¹Ø±Õ£©
-  uint8 paidAmount;		//µ±¶©µ¥ÊÇÒÑÖ§¸¶×´Ì¬£¬·µ»ØÖ§¸¶³É¹¦½ð¶î £¬ ·ñÔòÊÇ 0
+  uint32 paidAmount;		//µ±¶©µ¥ÊÇÒÑÖ§¸¶×´Ì¬£¬·µ»ØÖ§¸¶³É¹¦½ð¶î £¬ ·ñÔòÊÇ 0
 } sp_qrcode_t;
 
 //É豸²ÎÊý
@@ -204,6 +205,8 @@
   uint8 deviceno;
   uint8 local_deviceno;
   uint8 devphyid[4];
+  uint8 errmsg[32]; //Áª»úºǫ́·µ»Ø´íÎóÐÅÏ¢
+  uint16 errmsglen;
 
   sp_cardstate_t cardState;
   sp_sysconf_t sysconf;
@@ -222,19 +225,19 @@
 {
   uint8 fee_start;	//T°ÙºÁÉý¿ªÊ¼;
   uint8 fee_unit;	//µ¥´Î¿Û·Ñ¿ÉÓÃÁ÷Á¿£¨µ¥Î»:100ml£©
-  uint8 fee_amt;	//µ¥´Î¿Û·Ñ½ð¶î£¬ÒÔ·ÖΪµ¥Î»
+  uint8 fee_amt;	//µ¥´Î¿Û·Ñ½ð¶î£¬ÒÔÀåΪµ¥Î»
 } sp_feepara_t;
 
 //¿¨½á¹¹ÐÅÏ¢
 typedef struct
 {
   uint8 cardphyid[4];
-  uint8 citizen_cardno[12];	//ÊÐÃñºÅ
+  uint8 citizen_cardno[4];	//ÊÐÃñºÅ
   uint8 cardtype;
   uint8 expiredate[4];
 
-  uint16 waterlimit;		//µ¥´Î³öË®Á÷Á¿ÉÏÏÞ£¨100ml£©
-  uint16 amountlimit;		//µ¥´Î³öË®½ð¶îÉÏÏÞ (·Ö)
+  uint32 waterlimit;		//µ¥´Î³öË®Á÷Á¿ÉÏÏÞ£¨100ml£©
+  uint32 amountlimit;		//µ¥´Î³öË®½ð¶îÉÏÏÞ (Àå)
   uint32 cobillno;		//½»Ò×¶©µ¥±àºÅ
   uint8	permit;			//ÊÇ·ñÔÊÐíÏû·Ñ£¬0-ÔÊÐí£¬1-²»ÔÊÐí
   char limitmsg[45];		//ÏÞÖÆÏû·ÑÐÅÏ¢
diff --git a/supwisdom/sp_constant.h b/supwisdom/sp_constant.h
index ea79d09..6971775 100644
--- a/supwisdom/sp_constant.h
+++ b/supwisdom/sp_constant.h
@@ -8,35 +8,23 @@
 
 ////////////////////////////////////////////////////////////////////////////////
 #define RC_SUCCESS 						0 	// ³É¹¦
-#define RC_PSAM_ERR						1   //SAM¸´Î»Ê§°Ü
-#define RC_CARD_LOGIN					2	//ÑéÖ¤ÃÜԿʧ°Ü
-#define RC_CARD_READ					3	//¶Á¿¨Ê§°Ü
-#define RC_CARD_WRITE					4	//д¿¨Ê§°Ü
 #define RC_FLASH_ERR					5	//FLASH´íÎó
 #define RC_HARDWARE_ERR					6  //Ó²¼þ¼ÓÔØ´íÎó
 #define RC_FLASH_NO_RIGHT				7 //·Ç¿Éдflash
 
-#define RC_CARD_NORIGHT 				11	//¿¨ÎÞȨÏÞ
 #define RC_CARD_EXPIRED					12 	//¹ýÆÚ¿¨
 #define RC_CARD_AUTHENTICATION			13	//¿¨ÈÏ֤ʧ°Ü
-#define RC_CARD_LOST					14	//ºÚÃûµ¥¿¨
-#define RC_CARDNO_EXCEPT				17	//¿¨ºÅÒì³£
 #define RC_CARD_TIMEOUT					18	//ʹÓÃʱ¼äÌ«³¤
-#define RC_CARDBAL_EXCEPT				19	//¿¨Óà¶îÒì³£
-#define RC_CARDBAL_LACK					20	//¿¨Óà¶î²»×ã
 
 #define RC_DEVPHYID_NOTSET				21 	//É豸µØÖ·Î´ÉèÖÃ
-#define RC_FEERATE_NOTSET				22 	//·ÑÂÊδ³õʼ»¯
 #define RC_DEV_OFFLINE_ERROR			23  // É豸ÍÑ»ú¹¤×÷Ì«³¤
-#define RC_FILE09_CRC_ERR				25	////¼Ç¼CRC´íÎó
-#define RC_FILE10_CRC_ERR				26 	//Ë®¿ØÇ®°üCRC´íÎó
 #define RC_CARD_INVALID					27	//ÎÞЧ¿¨
-#define RC_FEENUM_ERROR					28	//·ÑÂʸöÊý´íÎó
 #define RC_NOTSUPPORT					29	//²»Ö§³Ö		
 #define RC_NOT_SAME_CARD				30	//²»Í¬¿¨
 
-#define RC_MODE_NOT_SUPPORT				42	//Ïû·Ñģʽ²»Ö§³Ö
 #define RC_UPDPROG_ERR					43	//Éý¼¶Ê§°Ü
+#define RC_WATER_LIMIT_OUT				44  // µ¥´ÎÁ÷Á¿³¬ÏÞ
+#define RC_AMOUNT_LIMIT_OUT				45  // µ¥´ÎÏû·Ñ½ð¶î³¬ÏÞ
 
 #define RC_CONFPARA_CRC_ERR   			55  //ÅäÖòÎÊýcrc´íÎó
 #define RC_TRANSDTL_FULL				58	//	Á÷Ë®ÒÑÂú
@@ -52,9 +40,6 @@
 #define RC_DEV_FAULT					66  //É豸ÒÉËÆ¹ÊÕÏ
 #define RC_DEV_NOSET_FLOWSENSOR_UNIT	67  //É豸Á÷Á¿¼ÆË㵥λδÉèÖÃ
 #define RC_COMM_TIMEOUT					68  //ͨѶ³¬Ê±
-#define STATUS_KEEPOPEN					1	//³£¿ª¿¨
-#define STATUS_CLOSED					0	//È¡Ïû³£¿ª¿¨
-
 #define RC_LIMIT_CONSUMPTION			70	//ÏÞÖÆÏû·Ñ
 
 #endif
diff --git a/supwisdom/sp_consume.c b/supwisdom/sp_consume.c
index 7545390..f7f5f94 100644
--- a/supwisdom/sp_consume.c
+++ b/supwisdom/sp_consume.c
@@ -313,6 +313,15 @@
 
   if(pos->purchase.prepaid_num > 0)
   {
+    if((pos->purchase.paid_num +pos->purchase.prepaid_num) > card->waterlimit)
+    {
+      return RC_WATER_LIMIT_OUT;
+    }
+    else if((pos->purchase.paid_sum +pos->purchase.prepaid_amt) > card->amountlimit)
+    {
+      return RC_AMOUNT_LIMIT_OUT;
+    }
+
     pos->purchase.paid_num += pos->purchase.prepaid_num;
     pos->purchase.paid_sum += pos->purchase.prepaid_amt;
     pos->purchase.prepaid_num = 0;
@@ -343,7 +352,7 @@
   }
   if(pos->purchase.paid_sum > 0)
   {
-    sprintf(msg,"¹²¼Æ %0.2fÔª",pos->purchase.paid_sum/100.0f);
+    sprintf(msg,"¹²¼Æ %0.3fÔª",pos->purchase.paid_sum/1000.0f);
     disp_hint_info_two(pos,"½áÊø¼Æ·Ñ",msg,DELAY_TIME2s);
   }
   else
@@ -364,7 +373,7 @@
   sp_valve_off();
   if(pos->purchase.paid_sum > 0)
   {
-    sprintf(msg,"¹²¼Æ %0.2fÔª",pos->purchase.paid_sum/100.0f);
+    sprintf(msg,"¹²¼Æ %0.3fÔª",pos->purchase.paid_sum/1000.0f);
     disp_hint_info_two(pos,"ÔÝÍ£¼Æ·Ñ",msg,DELAY_TIME2s);
   }
   else
@@ -375,6 +384,8 @@
 
 static void do_error(sp_pos_t* pos, uint16 errcode)
 {
+  sp_valve_off();
+
   if(errcode)
   {
     show_error(pos,"²Ù×÷ʧ°Ü:",errcode);
@@ -393,7 +404,7 @@
   switch(cardWorkState->current_state)
   {
   case CARDWORKSTATUS_NONE:
-    if(timer_get_ticker() - pos->cardState.firsttick < 1500)
+    if(timer_get_ticker() - pos->cardState.firsttick < 500)
     {
       break;
     }
@@ -440,8 +451,23 @@
     }
     cardWorkState->pause_status = 0;
     ret = do_work(pos, card);
+    if(RC_WATER_LIMIT_OUT == ret)
+    {
+      sp_valve_off();
+      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î³öË®ÉÏÏÞ", DELAY_TIME2s);
+      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
+      break;
+    }
+    else if(RC_AMOUNT_LIMIT_OUT == ret)
+    {
+      sp_valve_off();
+      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î½ð¶îÉÏÏÞ", DELAY_TIME2s);
+      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
+      break;
+    }
     if(ret)
     {
+      sp_valve_off();
       show_error(pos,"Ïû·Ñʧ°Ü",ret);
       err = do_stop(pos, card);
       if(err != 0)
@@ -451,16 +477,6 @@
       cardWorkState->current_state = CARDWORKSTATUS_ERROR;
       break;
     }
-    if(pos->purchase.used_num > card->waterlimit)
-    {
-      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î³öË®ÉÏÏÞ", DELAY_TIME2s);
-      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
-    }
-    else if(pos->purchase.paid_sum > card->amountlimit)
-    {
-      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î½ð¶îÉÏÏÞ", DELAY_TIME2s);
-      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
-    }
     cardWorkState->pause_tick = timer_get_ticker();
     break;
   case CARDWORKSTATUS_STOPPING:
@@ -480,7 +496,6 @@
     if(MEMCMP(pos->cardState.snr, card->cardphyid, 4) != 0)
     {
       cardWorkState->current_state = CARDWORKSTATUS_NONE;
-      break;
     }
     break;
   case CARDWORKSTATUS_ERROR:
@@ -659,7 +674,7 @@
     ret = sp_prepare_behalf_transdtl(pos, &CARD);
     if(ret)
     {
-      cardWorkState->errcode = RC_QRCODE_TIMEOUT;
+      cardWorkState->errcode = ret;
       cardWorkState->current_state = CARDWORKSTATUS_ERROR;
       break;
     }
@@ -703,8 +718,23 @@
     break;
   case CARDWORKSTATUS_WORKING:
     ret = do_work(pos, &CARD);
+    if(RC_WATER_LIMIT_OUT == ret)
+    {
+      sp_valve_off();
+      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î³öË®ÉÏÏÞ", DELAY_TIME2s);
+      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
+      break;
+    }
+    else if(RC_AMOUNT_LIMIT_OUT == ret)
+    {
+      sp_valve_off();
+      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î½ð¶îÉÏÏÞ", DELAY_TIME2s);
+      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
+      break;
+    }
     if(ret)
     {
+      sp_valve_off();
       show_error(pos,"Ïû·Ñʧ°Ü",ret);
       ret = do_stop(pos, &CARD);
       if(ret)
@@ -714,19 +744,9 @@
       cardWorkState->current_state = CARDWORKSTATUS_ERROR;
       break;
     }
-    if(pos->purchase.used_num >CARD.waterlimit)
-    {
-      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î³öË®ÉÏÏÞ", DELAY_TIME2s);
-      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
-    }
-    else if(pos->purchase.paid_sum > CARD.amountlimit)
-    {
-      disp_hint_info_two(pos, "Í£Ö¹³öË®","ÒÑ´ïµ¥´Î½ð¶îÉÏÏÞ", DELAY_TIME2s);
-      cardWorkState->current_state = CARDWORKSTATUS_STOPPING;
-    }
     /**È·ÈϳöË®ºó³¬¹ýµÈ´ýʱ¼äδ³öˮֹͣ³öË®**/
     CARD.qrcode.nowtime = sp_get_ticker();
-    if((CARD.qrcode.nowtime - CARD.qrcode.starttime) > CARD.qrcode.waittime*DELAY_TIME1s)
+    if((CARD.qrcode.nowtime - CARD.qrcode.starttime) >= CARD.qrcode.waittime*DELAY_TIME1s)
     {
       if(pos->purchase.used_num == 0)
       {
diff --git a/supwisdom/sp_data.c b/supwisdom/sp_data.c
index 2275abc..d87b918 100644
--- a/supwisdom/sp_data.c
+++ b/supwisdom/sp_data.c
@@ -4,8 +4,8 @@
 #include "sp_constant.h"
 #include "sp_display.h"
 
-#define record_behalf_len 19
-#define record_below_len 13
+#define record_behalf_len 23
+#define record_below_len 41
 
 //Ñ­»·¼Ç¼ÿһ±ÊÁ÷Ë®¼Ç¼µÄµØÖ·
 static uint16 sp_write_last_record(sp_pos_t* pos)
@@ -79,6 +79,7 @@
   memcpy(record.transtime, ctime+3, 3);
   record.cobillno = card->cobillno;
   memcpy(record.cardphyid, card->cardphyid, sizeof(card->cardphyid));
+  memcpy(record.cardno, card->citizen_cardno, sizeof(card->citizen_cardno));
   if(pos->paymode == PAYMODE_QRCODE)
   {
     record.transway = 2;
diff --git a/supwisdom/sp_display.c b/supwisdom/sp_display.c
index 76ab136..3ec3a1b 100644
--- a/supwisdom/sp_display.c
+++ b/supwisdom/sp_display.c
@@ -25,7 +25,7 @@
 void show_money(sp_pos_t* pos, uint32 money)
 {
   char msg[32];
-  sprintf(msg,"     %.02f Ԫ",money/100.0f);
+  sprintf(msg,"     %.03fԪ",money/1000.0f);
   disp_hint_info_two(pos,"ÀÛ¼ÆË®·Ñ:",msg,0);
 }
 
@@ -174,18 +174,6 @@
   char msg[32];
   switch(errcode)
   {
-  case RC_PSAM_ERR:
-    sprintf(msg, "%s", "SAM¸´Î»Ê§°Ü");
-    break;
-  case RC_CARD_LOGIN:
-    sprintf(msg, "%s", "ÑéÖ¤ÃØÔ¿Ê§°Ü");
-    break;
-  case RC_CARD_READ:
-    sprintf(msg, "%s", "¶Á¿¨Ê§°Ü");
-    break;
-  case RC_CARD_WRITE:
-    sprintf(msg, "%s", "д¿¨Ê§°Ü");
-    break;
   case RC_FLASH_ERR:
     sprintf(msg, "%s", "FLASHÒì³£");
     break;
@@ -195,60 +183,30 @@
   case RC_FLASH_NO_RIGHT:
     sprintf(msg, "%s", "FLASHÏÞÖÆ");
     break;
-  case RC_CARD_NORIGHT:
-    sprintf(msg, "%s", "¿¨ÎÞȨÏÞ");
-    break;
   case RC_CARD_EXPIRED:
     sprintf(msg, "%s", "¿¨ÒѹýÆÚ");
     break;
-  case RC_CARD_LOST:
-    sprintf(msg, "%s", "¿¨ÒÑËø¶¨");
-    break;
-  case RC_CARDNO_EXCEPT:
-    sprintf(msg, "%s", "¿¨Òì³£");
-    break;
   case RC_CARD_TIMEOUT:
     sprintf(msg, "%s", "ʹÓÃÌ«¾Ã");
     break;
-  case RC_CARDBAL_EXCEPT:
-    sprintf(msg, "%s", "Óà¶îÒì³£");
-    break;
-  case RC_CARDBAL_LACK:
-    sprintf(msg, "%s", "ÇëÁª»úÏû·Ñ");
-    break;
   case RC_DEVPHYID_NOTSET:
     sprintf(msg, "%s", "δÉèÖûúºÅ");
     break;
-  case RC_FEERATE_NOTSET:
-    sprintf(msg, "%s", "δÉèÖ÷ÑÂÊ");
-    break;
   case RC_DEV_OFFLINE_ERROR:
     sprintf(msg, "%s", "É豸ÍÑ»úÌ«¾Ã");
     break;
   case RC_TRANSDTL_FULL:
     sprintf(msg, "%s", "Á÷Ë®ÒÑÂú");
     break;
-  case RC_FILE09_CRC_ERR:
-    sprintf(msg, "%s", "09CRC´íÎó");
-    break;
-  case RC_FILE10_CRC_ERR:
-    sprintf(msg, "%s", "10CRC´íÎó");
-    break;
   case RC_CARD_INVALID:
     sprintf(msg, "%s", "ÎÞЧ¿¨");
     break;
-  case RC_FEENUM_ERROR:
-    sprintf(msg, "%s", "·ÑÂʸöÊý´íÎó");
-    break;
   case RC_NOTSUPPORT:
     sprintf(msg, "%s", "²»Ö§³Ö");
     break;
   case RC_NOT_SAME_CARD:
     sprintf(msg, "%s", "²»Í¬¿¨");
     break;
-  case RC_MODE_NOT_SUPPORT:
-    sprintf(msg, "%s", "ģʽ²»Ö§³Ö");
-    break;
   case RC_UPDPROG_ERR:
     sprintf(msg, "%s", "Éý¼¶Ê§°Ü");
     break;
@@ -262,14 +220,14 @@
     sprintf(msg, "%s", "»úºÅ¹ý´ó");
     break;
   case RC_QRCODE_FAILURE:
-    sprintf(msg, "%s", "¶þάÂë»ñȡʧ°Ü");
-    break;
+  	disp_server_errmsg(pos,"»ñȡʧ°Ü",pos->errmsg,pos->errmsglen);
+  	return;
   case RC_QRCODE_TIMEOUT:
     sprintf(msg, "%s", "¶þάÂ볬ʱ");
     break;
   case RC_QRCODE_QUERY_FAIL:
-    sprintf(msg, "%s", "¶þάÂëÈÏ֤ʧ°Ü");
-    break;
+  	disp_server_errmsg(pos,"ÈÏ֤ʧ°Ü",pos->errmsg,pos->errmsglen);
+  	return;
   case RC_DEV_NOT_LOGIN:
     sprintf(msg, "%s", "É豸δǩµ½");
     break;
@@ -277,13 +235,13 @@
     sprintf(msg, "%s", "É豸ÒÉËÆ¹ÊÕÏ");
     break;
   case RC_DEV_NOSET_FLOWSENSOR_UNIT:
-    sprintf(msg, "%s", "Á÷Á¿¼ÆË㵥λδÉèÖÃ");
+    sprintf(msg, "%s", "¼ÆÁ¿µ¥Î»Î´ÉèÖÃ");
     break;
   case RC_CARD_AUTHENTICATION:
-    sprintf(msg, "%s", "Éí·ÝÈÏÖ¤³¬Ê±");
-    break;
+  	disp_server_errmsg(pos,"ÈÏ֤ʧ°Ü",pos->errmsg,pos->errmsglen);
+  	return;
   case RC_LIMIT_CONSUMPTION:
-    sprintf(msg, "%s", "¸ÃÓû§±»ÏÞÖÆÏû·Ñ");
+    sprintf(msg, "%s", "ÏÞÖÆÏû·Ñ");
     break;
   default:
     sprintf(msg,"´íÎóÂë=0x%04x",errcode);
diff --git a/supwisdom/sp_util.c b/supwisdom/sp_util.c
index df70b13..5b10833 100644
--- a/supwisdom/sp_util.c
+++ b/supwisdom/sp_util.c
@@ -255,13 +255,19 @@
 }
 void sp_valve_on(void)
 {
-  valve_sta_set(valve_state_on);
-  valve_ctrl();
+  if(!valve_sta_get())
+  {
+    valve_sta_set(valve_state_on);
+    valve_ctrl();
+  }
 }
 void sp_valve_off(void)
 {
-  valve_sta_set(valve_state_off);
-  valve_ctrl();
+  if(valve_sta_get())
+  {
+    valve_sta_set(valve_state_off);
+    valve_ctrl();
+  }
 }
 uint8 sp_valve_state(void)
 {