某报价预算软件(PB9程序) Ver 5.1 注册验证分析(一)
某报价预算软件(PB9程序) Ver 5.1 注册验证分析 (一)
日期:2005年9月6日 破解人:Baby2008
-------------------------------------------------------------------------------------------------------------------------
『软件名称』:某报价预算软件 成套版 Ver 5.1
『软件大小』:34.5MB
『下载地址』:商业软件,不便提供,看懂得自己搜索
『软件介绍』:
『保护方式』:注册文件+注册码保护
『破解声明』:初学Crack,只是感兴趣,个人感觉PB程序分析破文不多,由我来抛砖引玉吧
『破解工具』:OllyDbg.V1.10 ,PBKiller (感谢作者:kivens)
『破解过程』:
一、安装序列号破解
安装时需要软件安装序列号,那先分析一个软件安装序列号;
运行安装程序,到达序列号输入界面,由于安装包是由Setup Factory 7.0制作的,安装程序会在安装过程中会产生一个临时进程来完成安装,
破解安装序列号需要切换到临时进程,启动fllyODBG,附加进程:
未命名的窗口,项目 35
进程=00000FC4
名称=irsetup
窗口=产品序列号
路径=C:\DOCUME~1\wxb\LOCALS~1\Temp\irsetup.exe //安装程序临时进程
设置Point H(万能断点),输入安装序列号1234567890,下一步,OD中断并返回主流程:
:
0042E1DC FF15 4C144400 call dword ptr ds:[<&USER32.GetWindowTextA>] ; USER32.GetWindowTextA
0042E1E2 6A FF push -1 ; 返回这里
0042E1E4 8BCF mov ecx,edi
0042E1E6 E8 BA2D0000 call irsetup.00430FA5
0042E1EB EB 13 jmp short irsetup.0042E200
0042E1ED 8BCE mov ecx,esi
0042E1EF E8 CA1E0000 call irsetup.004300BE
0042E1F4 85C0 test eax,eax
0042E1F6 74 08 je short irsetup.0042E200
0042E1F8 57 push edi
0042E1F9 8BC8 mov ecx,eax
0042E1FB E8 52FFFFFF call irsetup.0042E152
0042E200 8B07 mov eax,dword ptr ds:[edi] ; 试炼码
0042E202 5F pop edi
0042E203 5E pop esi
0042E204 8B40 F8 mov eax,dword ptr ds:[eax-8]
0042E207 C2 0800 retn 8
………(省略代码N行)…………………
00415607 E8 53B60100 call irsetup.00430C5F
0041560C 8065 FC 00 and byte ptr ss:[ebp-4],0
00415610 8D4D E8 lea ecx,dword ptr ss:[ebp-18]
00415613 E8 5AB50100 call irsetup.00430B72
00415618 FF75 08 push dword ptr ss:[ebp+8]
0041561B FF75 F0 push dword ptr ss:[ebp-10]
0041561E E8 A2CA0000 call irsetup.004220C5
堆栈信息:
0012F510 00CBA9E8 ASCII "1234567890"
0012F514 00AF20F0 ASCII "X2D"
0012F518 00AF20F0 ASCII "X2D"
0012F51C 0012F50C
0012F520 00CAF648 ASCII "9896-7818-3668-5118"
0012F524 00000000
0012F528 00CAF648 ASCII "9896-7818-3668-5118" //安装序列号
得到安装序列号:9896-7818-3668-5118 顺利完成安装过程。
二、注册信息文件分析
程序为PB9编写,OD调试会在“PB解释器”里打转,还是用PB克星PBKiller (再次感谢作者:kivens,DePB 公开版本不支持PB9)反编译各事件代
码,源代码可读性非常的好,下面对各重要代码稍作解释:
注册界面生成注册信息按钮事件:
string ls_gsmc
string ls_gsdz
string ls_tel
string ls_fax
string ls_yb
string ls_lxr
string ls_zcm
string ls_zclm
string ls_ver
string ls_email
integer li_int_1
date ldt_zcrq
string ls_write_cpu
string ls_write_hard
string ls_write_macf
string ls_write_regpass
string ls_write_gsmc
string ls_jq
string ls_zcmc
string ls_yhzt
string ls_dqcs
string ls_bzcs
string ls_dqsj
string ls_zcsj
string ls_dlsj
date ldt_xtsj
long ll_zcsj
long ll_dqsj
long ll_dlsj
long ll_bzcs
long ll_dqcs
string ls_write_dqcs
string ls_write_bzcs
string ls_write_dlsj
string ls_write_zcsj
string ls_write_yhzt
string ls_write_dqsj
string ls_maxuser
string ls_shengji
long ll_cpu
string ls_rootpath
string ls_volumnename
ulong lul_volumenamesize
ulong lul_volumeserialnumber
ulong lul_maximumcomponentlength
ulong lul_filesystemflags
string ls_filesystemnamebuffer
ulong lul_filesystemnamesize
boolean lb_rtn = false
string ls_regpass
integer li_i
string li_j
string ls_docname
string ls_named
string ls_typename
integer li_value
integer ll_file
select int_1 , zclm , updateid , dwmc , ver from update_rq using sqlca;
/* SQL Parameters List
0-> :li_int_1
1-> :ls_zclm
2-> :ls_zcm
3-> :ls_gsmc
4-> :ls_ver
*/
//取得数据库内容为:
1,'N',' ',' ','MorrowBudget Ver5.1 '
if li_int_1 < 1 then
li_int_1 = 1 //重要,指续费次数,后面会用到
end if
if ls_zclm = "N" and (len(ls_zcm) < 1 or isnull(ls_zcm)) then
ls_zcm = parent.wf_xlh() //软件序列号,相当于软件ID,升级ID
update update_rq set updateid =' ' using sqlca; //保存ID
/* SQL Parameters List
0-> :ls_zcm
*/
commit using sqlca;
parent.cb_2.enabled = false
else
if (ls_zclm = "" or len(ls_zclm) < 1) and (len(ls_zcm) < 1 or isnull(ls_zcm)) then
ls_zcm = parent.wf_xlh()
update update_rq set updateid =' ' using sqlca;
/* SQL Parameters List
0-> :ls_zcm
*/
commit using sqlca;
parent.cb_2.enabled = false
else
if ls_zclm = "Y" then
messagebox("注册提示","本软件已经注册,注册公司: " + ls_gsmc)
return
end if
end if
end if
ls_gsmc = trim(parent.sle_1.text) //读取界面空间内容
parent.is_gsmc = f_get_spellcn(ls_gsmc)
ls_gsdz = trim(parent.sle_2.text)
ls_tel = trim(parent.sle_4.text)
ls_fax = trim(parent.sle_5.text)
ls_yb = trim(parent.sle_6.text)
ls_lxr = trim(parent.sle_3.text)
ls_email = trim(parent.sle_7.text)
update update_rq set gsdz =' ' , lxr =' ' , tel =' ' using sqlca; //保存
/* SQL Parameters List
0-> :ls_gsdz
1-> :ls_lxr
2-> :ls_tel
*/
if len(ls_gsmc) < 1 or isnull(ls_gsmc) then //开始判断合法性
messagebox("提示","公司名称必须为法定名称,重新命名!")
return
end if
if len(ls_gsdz) < 1 or isnull(ls_gsdz) then
messagebox("提示","公司地址必须为法定地址,重新命名!")
return
end if
if len(ls_tel) < 6 or isnull(ls_tel) then
messagebox("提示","电话号码必须真实,重新命名!")
return
end if
if len(ls_fax) < 6 or isnull(ls_fax) then
messagebox("提示","传真号码必须真实,重新命名!")
return
end if
if len(ls_yb) <> 6 then
messagebox("提示","邮政编码必须真实,重新命名!")
return
end if
if len(ls_lxr) < 0 or isnull(ls_lxr) then
messagebox("提示","联系人必须真实,重新命名!")
return
end if
ldt_xtsj = date(today()) //系统时间
select dqcs , yhzt , dqsj , zcsj , dlsj , bzcs from lcs using sqlca; //取数据
/* SQL Parameters List
0-> :ls_dqcs
1-> :ls_yhzt
2-> :ls_dqsj
3-> :ls_zcsj
4-> :ls_dlsj
5-> :ls_bzcs
*/
//取得的数据为,(经过加密)
dqcs,yhzt,dqsj,zcsj,dlsj,bzcs
'a1):K',' ','QcR=opaBoQWaH<t?a2ZvH-64#_cZX%L-p2rEb>?*\\aMoG','YcmwL%aZy{+aUsrba%lw)->9@&c+5Rc-eR]AbW}x2a\\cf','$2
\\5>,0.Ypa0aQ5859iHU-D({b8^<\\a-@>#J3bSv510g^','w3|wu-1M3G'
select maxuser from c_maxuser using sqlca; //最大用户数,结果为空,单机版没用到
/* SQL Parameters List
0-> :ls_maxuser
*/
ls_write_yhzt = ls_yhzt //为写注册信息文件准备变量
ls_write_dqsj = ls_dqsj
ls_write_zcsj = ls_zcsj
ls_write_dlsj = ls_dlsj
ls_write_bzcs = ls_bzcs
ls_write_dqcs = ls_dqcs
ls_maxuser = parent.wf_jiami(ls_maxuser) //加密wf_jiami
ls_shengji = string(li_int_1) + string(rand(99)) + string(rand(99)) + string(rand(99)) + string(rand(99))
ls_shengji = parent.wf_numtochar(ls_shengji) //数字转字符wf_numtochar
ls_shengji = parent.wf_jiami(ls_shengji)
ll_cpu = abs(getcpuid()) //CPU ID
if ll_cpu > 0 then //CPU ID 获取失败用随机数代替
ls_write_cpu = string(ll_cpu)
else
ls_write_cpu = "77" + string(rand(99)) + string(rand(99)) + string(rand(99)) + string(rand(99)) + string(rand(99))
end if
ls_rootpath = "C:"
ls_volumnename = space(256) //取 C:\ 磁盘序列号
lul_volumenamesize = 256
lul_maximumcomponentlength = 256
ls_filesystemnamebuffer = space(256)
lul_filesystemnamesize = 256
beep(1)
lb_rtn = false
lb_rtn = getvolumeinformationa
(ls_rootpath,ls_volumnename,lul_volumenamesize,lul_volumeserialnumber,lul_maximumcomponentlength,lul_filesystemflags,ls_files
ystemnamebuffer,lul_filesystemnamesize)
if lb_rtn = true then //取 C:\ 磁盘序列号用随机数代替
ls_write_hard = trim(string(lul_volumeserialnumber))
else
ls_write_hard = "68" + string(rand(99)) + string(rand(99)) + string(rand(99)) + string(rand(99)) + string(rand(99))
end if
ls_write_macf = f_mac() //网卡序列号
if ls_write_macf = "" or isnull(ls_write_macf) then //失败用随机数代替
ls_write_macf = "37" + string(rand(99)) + string(rand(99)) + string(rand(99)) + string(rand(99)) + string(rand(99))
end if
select regpass from c_gsxx using sqlca;
/* SQL Parameters List
0-> :ls_regpass
*/
if len(ls_regpass) < 1 or isnull(ls_regpass) then //变量用途未知,估计是升级口令之类的
ls_write_regpass = parent.wf_round() + parent.wf_round() + parent.wf_round()
end if
ls_write_cpu = parent.wf_numtochar(ls_write_cpu) //替换
ls_write_hard = parent.wf_numtochar(ls_write_hard)
ls_write_macf = parent.wf_numtochar(ls_write_macf)
ls_write_regpass = parent.wf_numtochar(ls_write_regpass)
ls_write_cpu = parent.wf_jiami(ls_write_cpu) //加密
ls_write_hard = parent.wf_jiami(ls_write_hard)
ls_write_macf = parent.wf_jiami(ls_write_macf)
ls_write_regpass = parent.wf_jiami(ls_write_regpass)
ls_jq = parent.wf_toserial() + "#" + string(year(today())) + string(month(today())) + string(day(today()))
ls_zcmc = "zhuce" + ls_jq + "good"
update c_gsxx set zcmc =' ' using sqlca; //重要,保存信息用于后面判断注册文件的合法性wf_toserial() 取得Windows安装时的用
户名称和公司名称
/* SQL Parameters List
0-> :ls_zcmc
*/
ls_jq = parent.wf_jiami(ls_jq)
ls_zcmc = ls_jq
for li_i = 1 to 50
li_j = parent.wf_round()
next
ls_named = ls_ver + ls_gsmc //注册信息文件名
ls_docname = ls_named
li_value = getfilesavename("保存文件",ls_docname,ls_named,"sps","sps Files (*.sps),*.sps")
if li_value = 1 then
if fileexists(ls_docname) then
if messagebox("操作提示",ls_docname + "文件已经存在,是否覆盖它",question!,yesno!) = 2 then
return
end if
end if
ll_file = fileopen(ls_docname,linemode!,write!,lockreadwrite!,replace!)
if ll_file = -1 then
messagebox("操作提示","文件打开操作失败")
return
end if
if filewrite(ll_file,ls_ver) = -1 then //软件版本
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_gsmc) = -1 then //公司名称
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_gsdz) = -1 then //公司地址
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_tel) = -1 then //电话
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_fax) = -1 then //传真
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_yb) = -1 then //邮编
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_lxr) = -1 then //联系人
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_email) = -1 then //邮件
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_zcm) = -1 then //软件注册码=Update ID
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_shengji) = -1 then //1 +随机数
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_cpu) = -1 then //CPU ID
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_hard) = -1 then //C:\ SerialNo
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_macf) = -1 then //网卡ID
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_regpass) = -1 then //随机数
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_zcmc) = -1 then // wf_jiami(ls_regowner + "**" + ls_regcompany #日期)
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_yhzt) = -1 then //用户状态
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_dqsj) = -1 then
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_zcsj) = -1 then
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_dlsj) = -1 then
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_bzcs) = -1 then
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_write_dqcs) = -1 then
messagebox("操作提示","文件写操作失败")
return
end if
if filewrite(ll_file,ls_maxuser) = -1 then //最大用户数
messagebox("操作提示","文件写操作失败")
return
end if
else
messagebox("操作提示","文件命名不合法,重新命名!")
return
end if
fileclose(ll_file)
messagebox("系统写文件成功","报价单数据包保存在~r~n" + ls_docname + "~r~n请将以上文件发送到指定的邮箱中")
parent.cb_2.enabled = false
close(parent)
return
涉及重要函数:wf_numtochar,wf_jiami,分析一下:
--------------------------------------------------------------------------
Function wf_jiami (加密)
--------------------------------------------------------------------------
string ls_source
string ls_parm
string ls_arry[91]
string ls_mima[]
string ls_hunxiao[3]
integer li_i
integer li_j
integer li_long
li_long = len(ls_parmstring)
for li_i = 1 to li_long
ls_mima[li_i] = mid(ls_parmstring,li_i,1)
next
ls_source = "0132456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ{},./?[]\|+=_-)(*&^%$#@!`:<>"
for li_i = 1 to 91
ls_arry[li_i] = right(left(ls_source,li_i),li_i - (li_i - 1))
next
for li_i = 1 to li_long
ls_parm = ls_parm + ls_arry[rand(91)] + ls_mima[li_i] + ls_arry[rand(91)] + ls_arry[rand(91)] + ls_arry[rand(91)] +
ls_arry[rand(91)]
next
return ls_parm
本人不会PB,只好将代码翻译为Delphi 7.0的代码,为做注册机做准备(下同):
Delphi 7.0实现如下:
Function wf_jiami(Parm: String): String;
Const
ls_source: Array[0..90] Of Char = '0132456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ{},./?[]\|+=_-)(*&^%$#@!
`:<>';
Var
i: Integer;
Begin
For i := 1 To Length(Parm) Do
Result := Result + ls_source[Random(90)] + Parm[i] + ls_source[Random(90)] + ls_source[Random(90)] + ls_source[Random
(90)];
End;
对应反函数:
--------------------------------------------------------------------------
Function wf_jiemi (解密)
--------------------------------------------------------------------------
string ls_source
string ls_parm
string ls_mima[]
string ls_hunxiao[3]
integer li_i
integer li_j
integer li_long
li_long = len(ls_parmstring)
for li_i = 1 to li_long
ls_mima[li_i] = mid(ls_parmstring,li_i,1)
next
for li_i = 2 to li_long step 5
ls_parm = ls_parm + ls_mima[li_i]
next
return ls_parm
Delphi 7.0实现如下:
Function wf_jiemi(Parm: String): String;
Var
i: Integer;
Begin
i := 2;
While i <= Length(Parm) Do
Begin
Result := Result + Parm[i];
i := i + 5;
End;
End;
另有字符替换函数:
--------------------------------------------------------------------------
Function wf_numtochar
--------------------------------------------------------------------------
string ls_mima[]
string ls_parming
integer li_i
integer li_len
li_len = len(ls_parm)
for li_i = 1 to li_len
ls_mima[li_i] = mid(ls_parm,li_i,1)
if ls_mima[li_i] = "0" then
ls_mima[li_i] = "a"
end if
if ls_mima[li_i] = "1" then
ls_mima[li_i] = "b"
end if
if ls_mima[li_i] = "2" then
ls_mima[li_i] = "c"
end if
if ls_mima[li_i] = "3" then
ls_mima[li_i] = "d"
end if
if ls_mima[li_i] = "4" then
ls_mima[li_i] = "e"
end if
if ls_mima[li_i] = "5" then
ls_mima[li_i] = "f"
end if
if ls_mima[li_i] = "6" then
ls_mima[li_i] = "g"
end if
if ls_mima[li_i] = "7" then
ls_mima[li_i] = "h"
end if
if ls_mima[li_i] = "8" then
ls_mima[li_i] = "i"
end if
if ls_mima[li_i] = "9" then
ls_mima[li_i] = "j"
end if
next
for li_i = 1 to li_len
ls_parming = ls_parming + ls_mima[li_i]
next
return ls_parming
Delphi 7.0实现如下:
Function wf_numtochar(Parm: String): String;
Var
i: Integer;
Begin
Result := Parm;
For i := 1 To Length(Parm) Do
If Parm[i] In ['0'..'9'] Then Result[i] := Char(Ord(Parm[i]) + $31);
End;
--------------------------------------------------------------------------
Function wf_chartonum
--------------------------------------------------------------------------
string ls_mima[]
string ls_parming
integer li_i
integer li_len
li_len = len(ls_parm)
for li_i = 1 to li_len
ls_mima[li_i] = mid(ls_parm,li_i,1)
if ls_mima[li_i] = "a" then
ls_mima[li_i] = "0"
end if
if ls_mima[li_i] = "b" then
ls_mima[li_i] = "1"
end if
if ls_mima[li_i] = "c" then
ls_mima[li_i] = "2"
end if
if ls_mima[li_i] = "d" then
ls_mima[li_i] = "3"
end if
if ls_mima[li_i] = "e" then
ls_mima[li_i] = "4"
end if
if ls_mima[li_i] = "f" then
ls_mima[li_i] = "5"
end if
if ls_mima[li_i] = "g" then
ls_mima[li_i] = "6"
end if
if ls_mima[li_i] = "h" then
ls_mima[li_i] = "7"
end if
if ls_mima[li_i] = "i" then
ls_mima[li_i] = "8"
end if
if ls_mima[li_i] = "j" then
ls_mima[li_i] = "9"
end if
next
for li_i = 1 to li_len
ls_parming = ls_parming + ls_mima[li_i]
next
return ls_parming
Delphi 7.0实现如下:
Function wf_chartonum(Parm: String): String;
Var
i: Integer;
Begin
Result := Parm;
For i := 1 To Length(Parm) Do
If Parm[i] In ['a'..'j'] Then Result[i] := Char(Ord(Parm[i]) - $31);
End;
至此,注册信息产生过程已经搞清楚了,产生的文件信息后面还可以再利用,分析一下很有必要。
--------------------------------------------------------------------------
三、注册授权文件分析
软件作者根据注册信息文件返回注册授权文件,看一下“注册”按钮对注册授权文件有什么要求:
注册按钮事件:
string ls_file
string ls_docname
string ls_named
string ls_typename
string ls_ver
integer li_value
string ls_gsmc
string ls_hard
string ls_cpu
string ls_maxuser
string ls_macf
string ls_regpass
long ll_file
string ls_regcompany
string ls_regowner
string ls_jq
string ls_jqmatch
string ls_zcm
string ls_yhzt
string ls_dqcs
string ls_bzcs
string ls_dqsj
string ls_zcsj
string ls_dlsj
string ls_zclm
string ls_dlsjold
string ls_dlsjnew
string ls_zcm1
date ldt_dlsjold
date ldt_dlsjnew
long ll_match
string ls_docname1
string ls_path
integer li_ren
boolean rtn = false
string ls_yhzt1
integer li_max
li_value = getfileopenname("保存文件",ls_docname,ls_named,"PAS","Pas Files (*.PAS),*.pas")
if li_value = 1 then
ls_file = ls_docname
end if
if not fileexists(ls_file) then
messagebox("操作提示","该文件不存在或者您并没有输入文件的位置")
return
end if
ll_file = fileopen(ls_file,linemode!,read!,lockreadwrite!,replace!) //开始读取注册文件
if ll_file = -1 then
messagebox("操作提示","文件打开操作失败,确定文件的格式为.PAS")
return
end if
if fileread(ll_file,ls_ver) = -1 then
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(1)) //软件版本
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_zcm) = -1 then
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(1)) //软件注册码 Update ID
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_gsmc) = -1 then //公司名称
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(1))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_hard) = -1 then //硬盘序列号
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(2))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_cpu) = -1 then //CPU ID
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(3))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_macf) = -1 then //网卡 ID
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(4))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_regpass) = -1 then //随机数?
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(5))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_jqmatch) = -1 then //重要,判断是否是非法注册文件
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(7))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_maxuser) = -1 then
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(6))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_yhzt) = -1 then //用户状态
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(6))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_dqcs) = -1 then
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(6))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_bzcs) = -1 then
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(6))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_dqsj) = -1 then //到期时间
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(6))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_zcsj) = -1 then //注册时间
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(6))
fileclose(ll_file)
return
end if
if fileread(ll_file,ls_dlsj) = -1 then //最后登入时间
messagebox("操作提示","文件读操作失败,确定文件的格式为.PAS" + "/" + string(6))
fileclose(ll_file)
return
end if
parent.is_gsmc = f_get_spellcn(ls_gsmc) //公司名称->转汉字拼音首字母
if len(ls_maxuser) > 10 then //最大用户数,单机版不用
ls_maxuser = mid(ls_maxuser,9,len(ls_maxuser) - 16)
else
ls_maxuser = ""
end if
select updateid , zclm from update_rq using sqlca;
/* SQL Parameters List
0-> :ls_zcm1
1-> :ls_zclm
*/
ls_dlsjnew = ls_dlsj //登入时间
ls_dlsjnew = parent.wf_jiemi(ls_dlsjnew)
ls_dlsjnew = parent.wf_chartonum(ls_dlsjnew) //字母替换
select dlsj from lcs using sqlca;
/* SQL Parameters List
0-> :ls_dlsjold
*/
ls_dlsjold = parent.wf_jiemi(ls_dlsjold)
ls_dlsjold = parent.wf_chartonum(ls_dlsjold)
ldt_dlsjold = date(ls_dlsjold)
ldt_dlsjnew = date(ls_dlsjnew)
ll_match = daysafter(ldt_dlsjold,ldt_dlsjnew)
if ls_zcm <> ls_zcm1 then
messagebox("操作提示","注册文件过期,请与慕龙公司联系")
halt
end if
if ls_zclm = "Y" then //是否已经注册标志
messagebox("操作提示","本软件已经注册过了,不能重复注册")
halt
end if
select zcmc from c_gsxx using sqlca; //注册名称
/* SQL Parameters List
0-> :ls_jq
*/
ls_jqmatch = parent.wf_jiemi(ls_jqmatch)
ls_jqmatch = "zhuce" + ls_jqmatch + "good" //重要标志,在产生文件时强调过
if not ls_jqmatch = ls_jq then
messagebox("注册错误!","非法注册!")
halt
end if
ls_hard = parent.wf_jiemi(ls_hard) //解密C: 盘序列号
ls_cpu = parent.wf_jiemi(ls_cpu) //CPU ID
li_ren = registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion","PathName",regstring!,ls_path)
if li_ren = -1 then
li_ren = registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows me\CurrentVersion","PathName",regstring!,ls_path)
end if
if li_ren = -1 then
li_ren = registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion","PathName",regstring!,ls_path)
end if
if li_ren = -1 then
li_ren = registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows 98\CurrentVersion","PathName",regstring!,ls_path)
end if
if li_ren = -1 then
ls_path = "c:"
end if
rtn = fileexists(ls_path + "\mrbdt.ini") //内容为注册名称和序列号
if not rtn then
ll_file = filecopy(parent.is_file + "\mlpath.txt",ls_path + "\mrbdt.ini")
fileclose(ll_file)
ls_docname1 = ls_path + "\mrbdt.ini"
ll_file = fileopen(ls_docname1,linemode!,write!,lockwrite!,replace!)
if ll_file = -1 then
messagebox("操作提示","注册失败,异常号:001")
fileclose(ll_file)
close(parent)
return
end if
if filewrite(ll_file,ls_gsmc) = -1 then
messagebox("操作提示","注册失败,异常号:002")
fileclose(ll_file)
close(parent)
return
end if
if filewrite(ll_file,ls_zcm) = -1 then
messagebox("操作提示","注册失败,异常号:003")
fileclose(ll_file)
close(parent)
return
end if
fileclose(ll_file)
end if
//分系统版本取windows安装时公司名称
li_ren = registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows
NT\CurrentVersion\Winlogon","DefaultDomainName",regstring!,ls_regcompany)
if li_ren = -1 then
registryget
("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Winlogon","DefaultDomainName",regstring!,ls_regcompany)
end if
if li_ren = -1 then
registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows
ME\CurrentVersion\Winlogon","DefaultDomainName",regstring!,ls_regcompany)
end if
if li_ren = -1 then
registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows 98
\CurrentVersion\Winlogon","DefaultDomainName",regstring!,ls_regcompany)
end if
//分系统版本取机器名称
li_ren = registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows
NT\CurrentVersion","RegisteredOwner",regstring!,ls_regowner)
if li_ren = -1 then
registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion","RegisteredOwner",regstring!,ls_regowner)
end if
if li_ren = -1 then
registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows
ME\CurrentVersion","RegisteredOwner",regstring!,ls_regowner)
end if
if li_ren = -1 then
registryget("HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows 98
\CurrentVersion","RegisteredOwner",regstring!,ls_regowner)
end if
if isnull(ls_regowner) then
ls_regowner = parent.is_gsmc //假如空,用软件注册时的公司名称代替
end if
if isnull(ls_regcompany) then //同上
ls_regcompany = parent.is_gsmc
end if
ls_regcompany = ls_regcompany + "^^^" + ls_regowner //更新标志
ls_yhzt1 = parent.wf_jiemi(ls_yhzt)
ls_yhzt1 = parent.wf_chartonum(ls_yhzt1)
if ls_yhzt1 = "2" then //系统状态,2为试用版 9为正式版
ls_zclm = "N"
else
ls_zclm = "Y"
end if
update c_gsxx set gsmc =' ' , zcmc =' ' using sqlca; //下面更新一下数据库信息
/* SQL Parameters List
0-> :ls_gsmc
1-> :ls_regcompany
*/
commit using sqlca;
update update_rq set dwmc =' ' , zclm =' ' , updateid =' ' , zcrq ={d '2005-08-31' } , updatepass ='8888' , ver =' ' using
sqlca;
/* SQL Parameters List
0-> :ls_gsmc
1-> :ls_zclm
2-> :ls_zcm
3-> :ldt_dlsjnew
4-> :ls_ver
*/
commit using sqlca;
update lcs set qhkg ='n' , yhzt =' ' , dqcs =' ' , bzcs =' ' , dqsj =' ' , zcsj =' ' , dlsj =' ' using sqlca;
/* SQL Parameters List
0-> :ls_yhzt
1-> :ls_dqcs
2-> :ls_bzcs
3-> :ls_dqsj
4-> :ls_zcsj
5-> :ls_dlsj
*/
commit using sqlca;
select count ( *) from c_maxuser using sqlca;
/* SQL Parameters List
0-> :li_max
*/
if not ls_maxuser = "A" then
if li_max > 1 then
delete from c_maxuser using sqlca;
insert into c_maxuser ( maxuser ) values ( ' ' ) using sqlca;
/* SQL Parameters List
0-> :ls_maxuser
*/
else
update c_maxuser set maxuser =' ' using sqlca;
/* SQL Parameters List
0-> :ls_maxuser
*/
end if
end if
update c_gsxx SET gsmc =' ' , cpu =' ' , hard =' ' , macf =' ' , regpass =' ' using sqlca;
/* SQL Parameters List
0-> :ls_gsmc
1-> :ls_cpu
2-> :ls_hard
3-> :ls_macf
4-> :ls_regpass
*/
if sqlca.sqlcode <> 0 then
rollback using sqlca;
messagebox("操作提示","机器注册出错1")
return
else
commit using sqlca;
messagebox("祝贺!","机器注册成功,请登陆并使用!")
parent.cb_2.enabled = false
openwithparm(w_xufeichenggong,ls_zcm)
end if
return
--------------------------------------------------------------------------
根据注册授权文件要求,结合注册信息文件的内容,用Delphi 7实现下注册授权文件如下:
Procedure TForm1.btn1Click(Sender: TObject); //读取注册信息
Var
Reg: TMemo;
Begin
If dlgOpenRegFile.Execute Then
Begin
Reg := TMemo.Create(Self);
Reg.Parent := Self;
Reg.WordWrap := False;
Reg.Visible := False;
Reg.Lines.LoadFromFile(dlgOpenRegFile.FileName);
If Reg.Lines.Count <> 22 Then
Begin
Application.MessageBox('选择的不是注册文件!', '信息提示', MB_OK + MB_ICONWARNING);
Exit;
End;
With Reg Do
Begin
edtgsmc.Text := Lines[1];
edtgsdz.Text := Lines[2];
edtlxr.Text := Lines[6];
edtyb.Text := Lines[5];
edtTel.Text := Lines[3];
edtFax.Text := Lines[4];
edtEmail.Text := Lines[7];
ls_ver := Lines[0];
ls_gsmc := Lines[1];
ls_gsdz := Lines[2];
ls_tel := Lines[3];
ls_fax := Lines[4];
ls_yb := Lines[5];
ls_lxr := Lines[6];
ls_email := Lines[7];
ls_zcm := Lines[8];
ls_shengji := Lines[9];
ls_write_cpu := Lines[10];
ls_write_hard := Lines[11];
ls_write_macf := Lines[12];
ls_write_regpass := Lines[13]; //wf_numtochar(18个字符)
ls_zcmc := Lines[14]; //zhuceLenovo User**Legend (Beijing) Limited#200594good
ls_write_yhzt := Lines[15]; //用户状态 9:正常 2:试用
ls_write_dqsj := Lines[16]; // 到期时间
ls_write_zcsj := Lines[17]; // 注册时间
ls_write_dlsj := Lines[18]; //最后登入时间
ls_write_bzcs := Lines[19];
ls_write_dqcs := Lines[20]; //到期次数
ls_maxuser := Lines[21]; //最大用户数
End;
Reg.Free;
End;
End;
Procedure TForm1.btn2Click(Sender: TObject);
Var
Reg: TMemo;
Begin
If (edtgsmc.Text = '') Or (edtgsdz.Text = '') Or (edtlxr.Text = '') Or (edtTel.Text = '') Then
Begin
Application.MessageBox('注册信息不全,请重新读取注册文件!', '信息提示', MB_OK + MB_ICONWARNING);
Exit;
End;
Reg := TMemo.Create(Self);
Reg.Parent := Self;
Reg.WordWrap := False;
Reg.Visible := False;
With Reg Do //生成注册授权文件
Begin
Lines.Add(ls_ver); //软件版本
Lines.Add(ls_zcm); //注册码 Update ID
Lines.Add(ls_gsmc); //公司名称
Lines.Add(ls_write_hard); //硬盘序列号 C:\
Lines.Add(ls_write_cpu); //CPU ID
Lines.Add(ls_write_macf); //MAC ID
Lines.Add(ls_write_regpass);
Lines.Add(ls_zcmc); //重要,判断注册文件是否有效
Lines.Add(ls_maxuser); //最大用户数
Lines.Add(wf_jiami('9')); //用户状态 9:正常 2:试用版
Lines.Add(ls_write_dqcs);
Lines.Add(ls_write_bzcs);
// Lines.Add(ls_write_dqsj); //到期时间
Lines.Add(wf_jiami(FormatDateTime('yyyy-m-d', Date - 330)));
// Lines.Add(ls_write_zcsj); //注册时间
Lines.Add(wf_jiami(FormatDateTime('yyyy-m-d', Date)));
Lines.Add(ls_write_dlsj); //最后登入时间
End;
dlgSaveRegFile.FileName := ls_ver + ' ' + ls_gsmc + ' 注册文件';
If dlgSaveRegFile.Execute Then
Begin
If UpperCase(Copy(dlgSaveRegFile.FileName, Length(dlgSaveRegFile.FileName) - 2, 3)) <> UpperCase('pas') Then
dlgSaveRegFile.FileName := dlgSaveRegFile.FileName + '.pas';
Try
Reg.Lines.SaveToFile(dlgSaveRegFile.FileName);
Except
Application.MessageBox('生成注册文件失败,请检查目标文件是否可读写。', '信息提示', MB_OK + MB_ICONSTOP);
End;
End;
Reg.Free;
End;
待续……
[培训]《安卓高级研修班(网课)》月薪三万计划,掌握调试、分析还原ollvm、vmp的方法,定制art虚拟机自动化脱壳的方法