Archive
Delphi Product SKU Related Functions
Jika pada artikel sebelumnya kita membahas bagaimana mengetahui apakah suatu aplikasi dikompilasi dengan menggunakan Delphi beserta versi SKU Delphi yang digunakan, maka pada kesempatan kali ini membahas fungsi / prosedur apa saja yang berkaitan dengan pengenalan versi SKU terhadap pembatasan akses komponen / package pada saat runtime yang digunakan oleh internal Delphi.
Delphi merilis beberapa versi produk yang ditujukan untuk segmen pasar tertentu, misalnya versi Architect / Enterprise, Professional dan Personal. Perbedaan masing – masing versi ini adalah terletak pada fasilitas yang disediakan serta akses komponen / package pada saat runtime. Misalnya akses komponen Multitier hanya untuk versi Enterprise.
Pada saat runtime, komponen / object tertentu melakukan pengecekan versi SKU pada event OnCreate untuk memastikan bahwa komponen / object tersebut hanya diperuntukkan oleh aplikasi yang dikompilasi dengan veri SKU tertentu saja.
Jika versi yang diperiksa diperbolehkan mengakses object tersebut, maka proses dilanjutkan, namun jika tidak akan tampil pesan kesalahan ‘Application is not licensed to use this feature’.
Nah tentunya Anda penasaran bagaimana Delphi melakukan pengecekan versi SKU. Sebenarnya cukup sederhana. Delphi membandingkan nilai pengenal versi SKU yang disimpan sebagai resource pada aplikasi, yaitu DVCLAL dengan untaian kode yang sudah disiapkan. Tentunya perbandingan ini dilakukan setelah proses dekripsi seperlunya.
Proses pengecekan versi SKU dilakukan oleh 2 prosedur yang terletak pada unit SysUtils, yaitu RCS untuk mengecek versi Enterprise dan RPR untuk versi Professional. Prosedur RCS akan melemparkan eksepsi jika aplikasi yang diperiksa tidak dikompilasi dengan versi Enterprise. Demikian pula dengan prosedur RPR, akan melemparkan eksepsi jika aplikasi yang diperiksa tidak dikompilasi dengan versi Professional atau versi Enterprise.
Untuk lebih jelasnya bagaimana prosedur RCS dan RPR bekerja, silahkan Anda simak sendiri didalam unit SysUtils, atau singkatnya berikut cuplikan kodenya:
function AL1(const P): LongWord; asm MOV EDX,DWORD PTR [P] XOR EDX,DWORD PTR [P+4] XOR EDX,DWORD PTR [P+8] XOR EDX,DWORD PTR [P+12] MOV EAX,EDX end; function AL2(const P): LongWord; asm MOV EDX,DWORD PTR [P] ROR EDX,5 XOR EDX,DWORD PTR [P+4] ROR EDX,5 XOR EDX,DWORD PTR [P+8] ROR EDX,5 XOR EDX,DWORD PTR [P+12] MOV EAX,EDX end; const AL1s: array[0..3] of LongWord = ($FFFFFFF0, $FFFFEBF0, 0, $FFFFFFFF); AL2s: array[0..3] of LongWord = ($42C3ECEF, $20F7AEB6, $D1C2F74E, $3F6574DE); procedure ALV; begin raise Exception.CreateRes(@SNL); end; function ALR: Pointer; var LibModule: PLibModule; begin if MainInstance <> 0 then Result := Pointer(LoadResource(MainInstance, FindResource(MainInstance, 'DVCLAL', RT_RCDATA))) else begin Result := nil; LibModule := LibModuleList; while LibModule <> nil do begin with LibModule^ do begin Result := Pointer(LoadResource(Instance, FindResource(Instance, 'DVCLAL', RT_RCDATA))); if Result <> nil then Break; end; LibModule := LibModule.Next; end; end; end; function GDAL: LongWord; type TDVCLAL = array[0..3] of LongWord; PDVCLAL = ^TDVCLAL; var P: Pointer; A1, A2: LongWord; PAL1s, PAL2s: PDVCLAL; ALOK: Boolean; begin P := ALR; if P <> nil then begin A1 := AL1(P^); A2 := AL2(P^); Result := A1; PAL1s := @AL1s; PAL2s := @AL2s; ALOK := ((A1 = PAL1s[0]) and (A2 = PAL2s[0])) or ((A1 = PAL1s[1]) and (A2 = PAL2s[1])) or ((A1 = PAL1s[2]) and (A2 = PAL2s[2])); FreeResource(Integer(P)); if not ALOK then ALV; end else Result := AL1s[3]; end; procedure RCS; var P: Pointer; ALOK: Boolean; begin P := ALR; if P <> nil then begin ALOK := (AL1(P^) = AL1s[2]) and (AL2(P^) = AL2s[2]); FreeResource(Integer(P)); end else ALOK := False; if not ALOK then ALV; end; procedure RPR; var AL: LongWord; begin AL := GDAL; if (AL <> AL1s[1]) and (AL <> AL1s[2]) then ALV; end;
Nah untuk membuktikan kode diatas bekerja, saya telah membuat demo aplikasi yang saya kompilasi dengan Delphi 7 Enterprise dan Turbo Delphi 2006 Professional. Berikut cuplikan kodenya:
{ Delphi SKU Related Function Demo Created by Bayu Prasetio } unit SKUDemoUnit; interface uses Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls, ComCtrls; type TfrmSKUDependent = class(TForm) btnCheckSKU: TButton; lblLegend: TLabel; btnCallEnterprise: TButton; btnCallProfessional: TButton; stbAbout: TStatusBar; procedure btnCheckSKUClick(Sender: TObject); procedure btnCallEnterpriseClick(Sender: TObject); procedure btnCallProfessionalClick(Sender: TObject); private { Private declarations } public { Public declarations } end; var frmSKUDependent: TfrmSKUDependent; implementation {$R *.dfm} procedure TfrmSKUDependent.btnCallEnterpriseClick(Sender: TObject); begin try RCS; MessageDlg('This demo is compiled by Delphi Enterprise SKU', mtInformation, [mbOK], 0); except Raise; end; end; procedure TfrmSKUDependent.btnCheckSKUClick(Sender: TObject); begin try RCS; // check for Enterprise / Client-Server SKU MessageDlg('Enterprise SKU', mtInformation, [mbOK], 0); except try RPR; //check for Professional SKU MessageDlg('Professional SKU', mtInformation, [mbOK], 0); except MessageDlg('Personal SKU', mtInformation, [mbOK], 0); end; end; end; procedure TfrmSKUDependent.btnCallProfessionalClick(Sender: TObject); begin try RPR; MessageDlg('This demo is compiled by Delphi Enterprise or Professional SKU', mtInformation, [mbOK], 0); except Raise; end; end; end.
Nah, jika kode diatas dikompilasi dengan Delphi 7 Enterprise, pada saat dijalankan berikut hasilnya:
Aksi tombol ‘Check SKU’ pada Delphi 7 Enterprise
Aksi tombol ‘Force Call Enterprise Function(RCS)’ pada Delphi 7 Enterprise
Aksi tombol ‘Force Call Professional Function(RPR)’ pada Delphi 7 Enterprise
Nah, jika kode dikompilasi dengan Turbo Delphi 2006 Professional, hasil yang diperoleh akan berbeda.
Aksi tombol ‘Check SKU’ pada Turbo Delphi 2006 Professional
Aksi tombol ‘Force Call Enterprise Function(RCS)’ pada Turbo Delphi 2006 Professional
Aksi tombol ‘Force Call Professional Function(RPR)’ pada Turbo Delphi 2006 Professional
Semoga bermanfaat.
Is Application Built With Delphi
Pada artikel kali ini akan dibahas sesuatu yang lain dari biasanya, yaitu mengetahui apakah suatu aplikasi dikompilasi dengan menggunakan Delphi beserta versi SKU Delphi yang digunakan. Dan artikel ini tidak akan menggunakan pemrograman sedikitpun, cukup dengan menggunakan tool saja.
Untuk mengetahuinya, cukup dengan melihat resource data yang disimpan pada file aplikasi yang diinginkan dengan menggunakan tool Resource Editor. Disini saya menggunakan tool XN Resource Editor versi 3.0.0.1 buatan Colin Wilson.
Buka file executable yang ingin diketahui melalui XNResourceEditor. Dalam kasus ini saya menggunakan file XNResourceEditor.exe itu sendiri. 🙂 Kemudian pada menu navigasi yang terletak di sebelah kiri, expand item RC Data. Jika terdapat subitem DVCLAL, maka aplikasi tersebut dikompilasi dengan Delphi atau BCB. Proses investigasi dapat diteruskan.
Kemudian expand item DVCLAL, pilih language yang ada, dalam hal ini umumnya Language Neutral atau 1033 dan lihat deretan nilai hexadecimal 16-byte yang ditampilkan pada layar sebelah kanan.
Deretan nilai tersebut adalah pengenal versi SKU Delphi yang digunakan. Berikut arti dari deretan nilai tersebut:
- Personal: 23 78 5D 23 B6 A5 F3 19 43 F3 40 02 26 D1 11 C7
- Professional: A2 8C DF 98 7B 3C 3A 79 26 71 3F 09 0F 2A 25 17
- Enterprise: 26 3D 4F 38 C2 82 37 B8 F3 24 42 03 17 9B 3A 83
Nah sangat mudah bukan? Pada artikel selanjutnya akan saya bahas fungsi / prosedur apa saja yang berkaitan dengan pengenalan versi SKU terhadap pembatasan akses komponen / package pada saat runtime yang digunakan oleh internal Delphi.
Semoga bermanfaat.
NB: Credits go to Robert Kozak for his idea and Bruce McGee for his IsDelphi tool.
Server Down, Harddisk Error dan Marhaban Yaa Ramadhan
Lama tak sua, baru kali ini sempat posting karena sibuk dengan deploy, tes dan implementasi beberapa aplikasi di kantor daerah. pada saat itu pula ServerMerdeka sempat down dengan jangka waktu yang cukup lama, berhari – hari. Walhasil domain bprasetio.or.id pun terkena imbasnya, tidak dapat diakses selama berhari-hari.
Peristiwa yang tidak kalah menyedihkan adalah rusaknya harddisk laptop saya pada hari minggu dini hari tanggal 9 September 2007. Peristiwa ini terjadi secara tidak terduga, selagi asik ngoprek, tiba2 terdengar suara ‘klek-klek-klek’ dan kemudian muncullah BSOD (Blue Scree Of Death). Sontan, komputer di restart, tapi suara klek2 tersebut kembali muncul dan harddisk tidak dapat dideteksi.
Melepas harddisk, memasangkannya di dalam harddisk-enclosure dan kemudian menyambungkan ke komputer via USB memberikan hasil yang sama, suara ‘klek’ dan harddisk yang tidak dapat dideteksi. Ah.. hilang semua arsip.. Tapi untunglah saya sudah ada backup walaupun tidak 100%, minimal saya bisa melakukan rekonstruksi dokumen aktual berdasarkan backup yang ada. Beberapa file download dari internet dapat diperoleh kembali, namun beberapa tool kecil yang baru dikembangkan sekitar 2 minggu terakhir tidak dapat diselamatkan, termasuk DelphiPackageSelector, ServerMonitoring dan versi terbaru dari Aplikasi Server untuk kantor yang belum sempat saya backup. 😦
Tapi sudahlah, life goes on, saya masih bisa melakukan rekonstruksi arsip dari backup yang ada, dan yang terpenting, bulan suci Ramadhan sudah dekat, mari kita sambut bulan yang penuh berkah dengan perasaan yang senang, hati yang bersih dan saling memaafkan agar ibadah puasa dapat kita tunaikan dengan lebih afdol.
Marhaban yaa Ramadhan, mohon maaf lahir dan batin. 🙂