Ejemplo n.º 1
0
int HDDEV::UnPackResponseStruct(HD8583STRUCT& resp,MESSAGETYPE* msg_type,
                                void* buf,size_t buflen)
{
    short datalen;
    HDISO8583Msg msg;
    char * input = (char*)buf;
    BUF_2_SHORT(datalen,input);
    if(datalen > buflen - 2)
        return -1;
    *msg_type = (MESSAGETYPE)(input[2] & 0xFF);
    unsigned char zero[2] = {0x00,0x00};
    if(msg.Unpack(resp,input+3,datalen-1) > 0)
    {
        // 比较 MAC 地址
        if(ACE_OS::memcmp(resp->mac,zero,2))
        {
            // 2 byte 长度, 2 byte mac 码
            unsigned short i = GenerateCRC16((unsigned char*)input+2,buflen-4);
            unsigned char tmp[4] = "";
            SHORT_2_BUF(i,tmp);
            /*tmp[0] = (unsigned char)((i & 0xFF00) >> 8);
            tmp[1] = (unsigned char)(i & 0xFF);*/
            tmp[2] = tmp[0];
            tmp[0] = tmp[1];
            tmp[1] = tmp[2];
            for(int i = 0; i < 2; ++i)
                for(int j = 0; j < 4; ++j)
                    tmp[i] ^=  KsgGetGateway()->GetConfig()->_workKey[i+j*2];

            return (ACE_OS::memcmp(resp->mac,tmp,2) == 0) ? 0 : -1;
        }
        return 0;
    }
    return -1;
}
Ejemplo n.º 2
0
size_t HDDEV::PackRequestStruct(HD8583STRUCT& req,MESSAGETYPE msg_type
                                ,void* buf,size_t maxlen,bool with_crc )
{
    HDISO8583Msg msg;
    char * output = (char*)buf;
    char * bitmap = output+3;
    size_t packlen = msg.Pack(req,output+3,maxlen-3);
    if(packlen <= 0)
        return 0;
    output[2] = (char)msg_type;
    packlen++;
    if(with_crc)
    {
        bitmap[FIELD_MACOFBASALBITMAP/8] |= 1 << (7 - FIELD_MACOFBASALBITMAP % 8);
        unsigned short i = GenerateCRC16((unsigned char*)output+2,static_cast<uint16>(packlen));

        output[packlen+3] = i % 0x100;
        output[packlen+2] = i / 0x100;
        for(i = 0; i < 4; ++i)
        {
            output[packlen+2] ^= KsgGetGateway()->GetConfig()->_workKey[i*2];
            output[packlen+3] ^= KsgGetGateway()->GetConfig()->_workKey[i*2+1];
        }
        packlen+=2;
    }
    short tmp = static_cast<short>(packlen);
    SHORT_2_BUF(tmp,output);
    return packlen+2;
}
Ejemplo n.º 3
0
int HDDEV::HDParsePosRecord(BYTE* buf,TRADERECORDSTRUCT* trade)
{
    BUF_2_INT(trade->CardNumber,buf);
    BUF_2_INT(trade->Balance,buf+4);
    BUF_2_INT(trade->Amount,buf+8);
    trade->Year = *(buf+12);
    trade->Month = *(buf+13);
    trade->Day = *(buf+14);
    trade->Hour = *(buf+15);
    trade->Minute = *(buf+16);
    trade->Second = *(buf+17);
    BUF_2_SHORT(trade->TraceOfEW,buf+18);
    BUF_2_INT(trade->TraceOfPOS,buf+20);
    BUF_2_INT(trade->OrgTransTrace,buf+24);
    BUF_2_INT(trade->OperatorID,buf+28);
    BUF_2_INT(trade->TerminalSN,buf+32); // 终端号
    BUF_2_SHORT(trade->AdditionalMoney,buf+36); // 管理费
    BUF_2_SHORT(trade->GoodsNumber,buf+38);
    trade->IndexOfEW = *(buf+40);
    if(trade->IndexOfEW > 0)
        trade->IndexOfEW--;
    trade->RecordType = *(buf+41);
    trade->ConsumeMode = *(buf+42);
    memcpy(trade->MAC,buf+43,4);
    uint16 i = GenerateCRC16(buf,43);
    unsigned char tmp[4] = "";
    SHORT_2_BUF(i,tmp);
    /*tmp[0] = (unsigned char)((i & 0xFF00) >> 8);
    tmp[1] = (unsigned char)(i & 0xFF);*/
    tmp[2] = tmp[0];
    tmp[0] = tmp[1];
    tmp[1] = tmp[2];
    for(int i = 0; i < 2; ++i)
        for(int j = 0; j < 4; ++j)
            tmp[i] ^=  KsgGetGateway()->GetConfig()->_workKey[i+j*2];
    return (ACE_OS::memcmp(trade->MAC,tmp,2) == 0) ? 0 : -1;
    /*if( (i & 0xFF) != trade->MAC[1] || ((i & 0xFF00)>>8) != trade->MAC[0])
    	return -1;
    return 0;
    */
}
Ejemplo n.º 4
0
int __stdcall decrypt_elec_card_pwd(int cut_id,const char seedkey[32],const char mpwd[64],char pwd[8])
{
	char temp[17],temp1[17],buf[17];
	char encrypt_seed[65];
	unsigned char radom_seed[4];
	keyInstance key_inst;
	cipherInstance cipher_inst;
	int i,len;
	static const int max_pwd_len = 8;

	memset(&key_inst,0,sizeof key_inst);
	memset(&cipher_inst,0,sizeof cipher_inst);


	// 读取随机种子
	memcpy(temp,mpwd,8);
	memset(temp1,0,sizeof temp1);
	for(i = 0;i < 8;i+=2)
	{
		memcpy(temp1,temp+i,2);
		radom_seed[i/2] = (unsigned char)strtoul(temp1,NULL,16);
	}

	// 计算种子密钥
	memset(encrypt_seed,0,sizeof encrypt_seed);
	for(i = 0;i < 32;++i)
		encrypt_seed[i] = seedkey[i] ^ radom_seed[i%4];
	CalcMD5((unsigned char*)encrypt_seed,32,(unsigned char*)temp);
	memset(encrypt_seed,0,sizeof encrypt_seed);
	for(i = 0; i < 16 ;++i)
		sprintf(encrypt_seed+i*2,"%02X",(unsigned char)temp[i]);


	// 解密
	if(makeKey(&key_inst,DIR_DECRYPT,128,(char*)encrypt_seed)==FALSE)
	{
		return -1;
	}
	if(cipherInit(&cipher_inst,MODE_CBC,NULL)==FALSE)
	{
		return -1;
	}

	memset(temp1,0,sizeof temp1);
	memset(temp,0,sizeof temp);
	for(i = 0;i < 32; i+=2)
	{
		memcpy(temp1,mpwd+12+i,2);
		temp[i/2] = (unsigned char)strtoul(temp1,NULL,16);
	}
	memset(temp1,0,sizeof temp1);
	len = blockDecrypt(&cipher_inst,&key_inst,(BYTE*)temp,16*8,(BYTE*)temp1);

	for(i=0;i < max_pwd_len;++i)
		buf[i] = temp1[i] ^ radom_seed[i%4];
	

	// 计算密码
	sprintf(temp,"%08X",cut_id);
	for(i = 0;i < max_pwd_len;++i)
		temp1[i] = temp1[i] ^ temp[i];
	// CRC 校验
	uint16 crc = GenerateCRC16((unsigned char*)temp1,max_pwd_len);
	memset(temp,0,sizeof temp);
	sprintf(temp,"%04X",crc);
	if(strncmp(temp,mpwd+8,4))
	{
		return -2;
	}
	memcpy(pwd,buf,max_pwd_len);
	//memcpy(pwd,temp1,max_pwd_len);
	
	return 0;
}
Ejemplo n.º 5
0
int __stdcall encrypt_elec_card_pwd(int cut_id,const char seedkey[32],const char pwd[8],char mpwd[64])
{
	static const int max_pwd_len = 8;
	keyInstance key_inst;
	cipherInstance cipher_inst;
	unsigned char buf[16] = "";
	char temp[16] = "";
	char temp2[16] = "";
	char pwd_str[max_pwd_len*2+1] = "";
	unsigned char decrypt_buf[16] = "";
	char encrypt_seedkey[64] = "";
	unsigned char decrypt_str[64] = "";
	time_t radom_seed = time(NULL);
	int len,i,j,pwd_len;
	memset(&key_inst,0,sizeof key_inst);
	memset(&cipher_inst,0,sizeof cipher_inst);
	
	for(i = 0;i < max_pwd_len;++i)
	{
		switch(pwd[i])
		{
		case ' ':
		case '\t':
		case '\r':
		case '\n':
		case '\'':
		case '"':
		case '%':
		case '_':
			return -2;
		default:
			break;
		}
	}
	pwd_len = strlen(pwd);
	if(pwd_len > max_pwd_len)
		return -3;
	// 取4位随机种子
	srand((unsigned int)radom_seed);
	for(i = 0;i < 4;++i)
		buf[i] = (unsigned char)(rand() % 0xFF);

	// 密码不足8位右补空格
	memcpy(pwd_str,pwd,pwd_len);
	for(i=pwd_len;i < max_pwd_len;++i)
		pwd_str[pwd_len] = ' ';
	for(i=0;i < max_pwd_len;++i)
		pwd_str[i] ^= buf[i%4];

	// 加密的密钥
	for(i = 0;i < max_pwd_len;++i)
		pwd_str[max_pwd_len+i] = pwd_str[i] | (!temp[i]);
	memcpy(pwd_str+max_pwd_len,pwd_str,max_pwd_len);

	
	// 计算种子密钥
	memset(encrypt_seedkey,0,sizeof encrypt_seedkey);
	for(i = 0; i < 32 ;++i)
		encrypt_seedkey[i] = seedkey[i] ^ buf[i%4];
	CalcMD5((unsigned char*)encrypt_seedkey,32,(unsigned char*)temp);
	memset(encrypt_seedkey,0,sizeof encrypt_seedkey);
	for(i = 0,j = 0;i < 16; ++i)
		j += sprintf(encrypt_seedkey+j,"%02X",(unsigned char)temp[i]);


	// 计算CRC
	sprintf(temp,"%08X",cut_id);
	memset(temp2,0,sizeof temp2);
	for(i = 0;i < max_pwd_len;++i)
		temp2[i] = pwd_str[i] ^ temp[i];
	uint16 crc = GenerateCRC16((unsigned char *)temp2,max_pwd_len);
	sprintf(temp,"%04X",crc);
	memcpy(buf+4,temp,4);
	
	

	// 进行加密
	if(makeKey(&key_inst,DIR_ENCRYPT,128,encrypt_seedkey)==FALSE)
	{
		return -1;
	}
	if(cipherInit(&cipher_inst,MODE_CBC,NULL)==FALSE)
	{
		return -1;
	}
	len = blockEncrypt(&cipher_inst,&key_inst,(unsigned char*)pwd_str,16*8,decrypt_str);
	if(len == 16*8)
	{
		// 8 个字符种子
		for(i = 0;i < 4; ++i)
			sprintf(mpwd+i*2,"%02X",(unsigned char)buf[i]);
		// 4 个字符CRC
		memcpy(mpwd+8,temp,4);
		// 8 个字符密码
		for(i = 0;i < 16;++i)
			sprintf(mpwd+12+i*2,"%02X",decrypt_str[i]);
		//mpwd[28] = '\0';
		return 0;
	}
	return -1;
}
Ejemplo n.º 6
0
int PASCAL WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdParam,
				   int nCmdShow)
{
	MSG msg;
	WINDOWPLACEMENT w;
	BOOL bQuit = FALSE;

	InitCommonControls();

	hInst = hInstance;

	// Find location of configuration file
	ConfigInit();

	/* Register our custom classes */
	RegisterWindowClasses();

	hMain = CreateWindow(szAppName,       /* window class name */
		szAppName,               /* window caption */
		WS_OVERLAPPEDWINDOW,     /* window style */
		0, 0, 0, 0,              /* initially zero size; changed below */
		NULL,                    /* parent window handle */
		NULL,                    /* window menu handle */
		hInstance,               /* program instance handle */
		NULL);	   	         /* creation parameters */

	if (!hMain)
	{
		char buf[256];
		DWORD err = GetLastError();
		sprintf(buf, "Error - Couldn't Create Client Window : %d", err);
		MessageBox(NULL, buf, "ERROR!", MB_OK);
		MainQuit(hMain);
		exit(1);
	}

	if (config.debug)
		CreateDebugWindow();

	if (lpszCmdParam && strlen(lpszCmdParam) > 0)
		ConfigOverride(lpszCmdParam);

	w.length = sizeof(WINDOWPLACEMENT);
	WindowSettingsLoad(&w);
	SetWindowPlacement(hMain, &w);

	D3DRenderInit(hMain);

	ModulesInit();   // Set up data structures for modules


/* attempt make a crc16 on the meridian.exe */
	GenerateCRC16();

	MainInitState(STATE_OFFLINE);

	UpdateWindow(hMain);

	while (!bQuit)
	{
		MainIdle();

		while (PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE))
		{
			if (!GetMessage(&msg, NULL, 0, 0))
			{
				bQuit = TRUE;
				break;
			}

			// Forward appropriate messages for tooltips
			if (state == STATE_GAME)
				TooltipForwardMessage(&msg);

			/* Handle modeless dialog messages separately */
			if ((hCurrentDlg == NULL || !IsDialogMessage(hCurrentDlg, &msg)))
			{
				TranslateMessage(&msg);
				DispatchMessage(&msg);
			}
		}
	}

	/* Unregister our custom classes--not good to leave them around */
	UnregisterWindowClasses();

	return msg.wParam;  // Return value of PostQuitMessage
}
Ejemplo n.º 7
0
static uint8 get_next_serial_no(z18_record_t *record)
{
	uint16 ret,crc;
	uint32 next_ptr;
	uint8 buffer[64];
	uint8 crc_buff[2];
	uint8 rec_date[7];
	uint8 i,main_error,flag;
	uint8 param_len = 26;
	// 先读取主参数表
	/*
	 * 记流水流程如下:
	 * 1。 先更新流水号值
	 * 2. 写卡
	 * 3. 更新流水状态
	 * 当第2步失败的时候,如果明确没有写到卡上,那这笔流水就直接覆盖掉, 因此我们直接读备块参数
	 */
	memset(buffer,0,sizeof buffer);
	memset(crc_buff,0,sizeof crc_buff);
	main_error = 1;
	ret = EeSysRead(POS_REC_PTR_ADDR,param_len,buffer);
	if(Z18_FAILED == ret)
	{
		debug_string("read ptr \n");
		return KNG_POS_HARDWARE_ERROR;
	}
	// 判断crc
	//debug_hex(buffer+8,25);
	crc = GenerateCRC16(buffer,param_len-2);
	//debug_string("crc[%u]",crc);
	set_2byte_int(crc,crc_buff);
	//debug_hex(crc_buff,2);
	if(memcmp(crc_buff,buffer+24,2) == 0)
	{
		//debug_string("main sect");
		// crc 校验正确
		for(i = 0;i < 3;++i)
		{
			if(buffer[i] != ~buffer[3+i])
				break;
			if(buffer[6+i] != ~buffer[9+i])
				break;
		}
		// 保存备参数的内容,以便将来恢复使用
		memcpy(g_z18pos.rec_buffer,buffer,sizeof(g_z18pos.rec_buffer));
		main_error = 0;
		// 在这种情况下因为最后一次写卡失败,主参数表已经被恢复,主备参数一致,这样就不需要再写备参数表
		if(g_z18pos.rec_status == 0)
		{
			//debug_string("sect backup");
			// 先备份到备区
			ret = EeSysWrite(POS_REC_BAK_PTR_ADDR,param_len,buffer);
			if(Z18_FAILED == ret)
			{
				debug_string("write ptr back\n");
				return KNG_POS_HARDWARE_ERROR;
			}
		}
	}
	if(main_error == 1)
	{
		// 读取备块
		memset(buffer,0,sizeof buffer);
		ret = EeSysRead(POS_REC_BAK_PTR_ADDR,param_len,buffer);
		if(Z18_FAILED == ret)
		{
			debug_string("read ptr back\n");
			return KNG_POS_HARDWARE_ERROR;
		}
		//debug_string("back sect"); 
		memset(crc_buff,0,sizeof crc_buff);
		crc = GenerateCRC16(buffer,24);
		set_2byte_int(crc,crc_buff);
		if(memcmp(crc_buff,buffer+24,2) != 0)
		{
			debug_string("back ptr crc\n");
			// 备块错误
			return KNG_POS_PARAM_ERROR;
		}
		// crc 校验正确
		for(i = 0;i < 3;++i)
		{
			if(buffer[i] != ~buffer[3+i])
			{
				debug_string("bak ptr crc\n");
				return KNG_POS_PARAM_ERROR;
			}
			if(buffer[6+i] != ~buffer[9+i])
			{
				debug_string("bak ptr crc\n");
				return KNG_POS_PARAM_ERROR;
			}
		}
		// 保存备参数的内容,以便将来恢复使用
		memcpy(g_z18pos.rec_buffer,buffer,sizeof(g_z18pos.rec_buffer));
	}
	// 写主区
	record->serial_no = get_4byte_int(buffer+12);
	g_z18pos.serial_no = record->serial_no;
	g_z18pos.rec_wr_ptr = get_3byte_int(buffer);
	g_z18pos.rec_rd_ptr = get_3byte_int(buffer+6);
	g_z18pos.rec_ptr_flag = buffer[23];
	flag = g_z18pos.rec_ptr_flag;
	// 如果写记录指针与读记录指针相等,则认为记录已满
	
	if(z18pos_check_rec_full())
	{
		// flash 已经写满,重新开始
		debug_string("record full\n");
		return KNG_POS_REC_FULL;	
	}
	

	if(g_z18pos.rec_rd_ptr == 0x00)
	{
		g_z18pos.rec_rd_ptr = POS_RECORD_BEGIN_ADDR;
		set_3byte_int(POS_RECORD_BEGIN_ADDR,buffer+6);
		calc_not(buffer+6,3,buffer+9);
	}
	next_ptr = g_z18pos.rec_wr_ptr + POS_REC_LEN;
	if(next_ptr >= POS_RECORD_END_ADDR)
	{
		// flash 写到最后 ,需要从头开始
		next_ptr = POS_RECORD_BEGIN_ADDR;
		if(next_ptr <= g_z18pos.rec_rd_ptr )
            flag = 0x00;
        else
            flag = 0xFF;
	}
	//debug_string("get serial no");
	// 更新到下一条写记录地址
	set_3byte_int(next_ptr,buffer);
	calc_not(buffer,3,buffer+3);

	// 累计金额
	g_z18pos.total_money = get_4byte_int(buffer+16);
	memcpy(rec_date,buffer+20,3);
    /*
	if(memcmp(g_z18pos.curr_time+1,rec_date,3) >0)
	{
		// 更新到下一天
		memcpy(buffer+20,g_z18pos.curr_time+1,3);
		// 写累计金额到前日累计金额
		ret = update_pre_total(g_z18pos.total_money);
		if(ret)
		{
			debug_string("update pre money\n");
			return ret;
		}
		g_z18pos.total_money = record->tx_money;
		debug_string("money[%lu][%lu]",g_z18pos.total_money,record->tx_money);
		memcpy(buffer+20,g_z18pos.curr_time+1,3);
	}
	else
	{
		g_z18pos.total_money += record->tx_money;
		debug_string("money[%lu][%lu]",g_z18pos.total_money,record->tx_money);
	}
	*/
	g_z18pos.total_money += record->tx_money;
	memcpy(g_z18pos.last_tx_date,buffer+20,3);
	// 更新当日累计金额
	set_4byte_int(g_z18pos.total_money,buffer+16);
	// 流水号
	set_4byte_int(record->serial_no+1,buffer+12);
	g_z18pos.serial_no++;
    g_z18pos.rec_wr_ptr = next_ptr;
	buffer[23] = flag;
	// 计算 crc
	crc = GenerateCRC16(buffer,24);
	set_2byte_int(crc,buffer+24);

    //debug_string("wr ptr[%lu]rd[%lu]serial[%lu]\n",g_z18pos.rec_wr_ptr,g_z18pos.rec_rd_ptr,g_z18pos.serial_no);
	ret = EeSysWrite(POS_REC_PTR_ADDR,param_len,buffer);
	if(ret == Z18_OK)
	{
        g_z18pos.rec_ptr_flag = flag;
		return 0;
	}
	
	debug_string("update ptr error\n");
	return KNG_POS_HARDWARE_ERROR;	
}
Ejemplo n.º 8
0
static uint8 record_serial(z18_record_t *record ,uint8 flag,uint8 data *buffer)
{
	uint8 offset,ret;
	// 根据 flag 的值来控制业务流程
	// 1 : 记录新的流水
	// 2 : 更新流水状态
	// 新记录流水
	if(flag==1)
	{
		offset = 0;
		// 版本号
		buffer[offset] = record->ver;
		offset++;
		// 设备物理 ID	
		memcpy(buffer+offset,g_z18pos.device_id,4);
		offset+=4;
		// 流水号
		set_4byte_int(record->serial_no,buffer+offset);
		offset+=4;
		// 交易卡号
		set_3byte_int(record->card_id,buffer+offset);
		offset +=3;
		// 入卡金额
		set_4byte_int(record->in_balance,buffer+offset);
		offset+=4;
		// 交易金额
		set_3byte_int(record->tx_money,buffer+offset);
		offset+=3;
		// 交易次数
		memcpy(buffer+offset,(uint8*)&record->tx_count,2);
		offset+=2;
		// 交易时间
		//str2bcd(record->tx_datetime,12,buffer+offset);
		memcpy(buffer+offset,record->tx_datetime,6);
		offset+=6;
		// 交易标志
		buffer[offset++] = record->tx_mark;
		// 交易类型
		buffer[offset++] = record->tx_type;
		// 钱包号
		buffer[offset++] = record->purse_no;
		// 前一笔流水
#ifdef SAVE_CARD_REC
		memcpy(buffer+offset,record->pre_device_id,4);
		offset+=4;
		memcpy(buffer+offset,record->pre_tx_time,4);
		offset+=4;
		set_4byte_int(record->pre_in_balance,buffer+offset);
		offset+=4;
		set_3byte_int(record->pre_tx_money,buffer+offset);
		offset+=3;
		buffer[offset++] = record->pre_tx_mark;
#else
		memset(buffer+offset,0x00,16);
		offset+=16;
#endif
		// 15 byte 保留
		offset+=15;
		// crc offset = 61
		record->tx_crc = GenerateCRC16(buffer,offset);
		set_2byte_int(record->tx_crc,buffer+offset);
		offset+=2;
		// 状态
		buffer[offset++] = record->tx_status;

		if(offset != POS_REC_LEN)
		{
			debug_string("error serial[%d]\n",(uint16)offset);
			return KNG_POS_PARAM_ERROR;
		}
		record->wr_ptr = g_z18pos.rec_wr_ptr;	
		//debug_string("wr ptr[%ld]",g_z18pos.rec_wr_ptr);
		ret = z18pos_write_eeprom(g_z18pos.rec_wr_ptr,offset,3,buffer);
		if(ret)
		{
            debug_string("record serial[%lu]\n",g_z18pos.rec_wr_ptr);
			return ret;
		}
		//get_next_wr_ptr();
		return 0;
	}
	else
	{
		// 更新交易标志
		buffer[27] = record->tx_mark;
		// 更新 crc 
		record->tx_crc = GenerateCRC16(buffer,POS_REC_LEN-3);
		set_2byte_int(record->tx_crc,buffer+61);
		// 更新 flash
		ret = z18pos_write_eeprom(record->wr_ptr,POS_REC_LEN,3,buffer);
		if(ret)
		{
            debug_string("upd rec,[%lu]\n",record->wr_ptr);
			return ret;
		}
		return 0;
		// 更新状态信息
	}
}