วันอังคารที่ 25 มีนาคม พ.ศ. 2557

C, Token-parsing preprocessor

ระหว่างปี 1995-1997 เป็นช่วงเปลี่ยนถ่ายจาก 16bit เป็น 32bit ในโลกของ Windows (ก่อนเป็น Win32) หลายท่านอาจจำได้ ปัญหาใหญ่ๆ ของ "C" โปรแกรมเมอร์หลายคนก็คือ การนำ Code เก่า หรือ DLL เก่าที่เป็น 16bit port มาเป็น 32bit ถ้ามีเวลาก็ค่อยๆ port โดยเริ่มจาก GlobalAlloc, GlobalLock, GlobalFree etc. แทนที่ด้วย malloc, free แบบที่ใช้ในปัจจุบัน

หลายคนที่มี code ใหญ่ๆ หรือมี DLL ที่ไม่มี code ไม่สามารถ port ได้ แต่ต้องการทำ Application ให้เป็น Win32 ก็มีทางเลือกอีกทางคือการใช้ Thunk layer ในการ เรียก 16bit API ด้วย 32bit app หรือ 16bit app เรียก 32bit API (อย่างหลังนี่ไม่ค่อยเห็น)

ซึ่งผมก็เป็นหนึ่งในนั้น....

เรื่องที่จะเล่าไม่ใช่เรื่อง Thunk layer หรือ Interoperability ของ Win16 กับ Win32 แต่เป็น Technique ที่ผมทำเอามาจาก Microsoft Excel source code (95) มาใช้กับการสร้าง Thunk layer ณ. เวลานั้น

Technique ที่ว่าคือ การทำ Token-parsing preprocessor, ซึ่งมีประโยชน์มากในการ define ชื่อ API ที่ทำให้เราสามารถจัดกลุ่มของ API ที่จะเรียกใช้เป็นหมวดหมู่ได้ง่าย (ดูตัวอย่างครับ)

#include <stdio.h>

#define GROUP_FIRST     _1_
#define GROUP_SECOND    _2_
#define TYPE_16         16
#define TYPE_32         32

#define METHOD_HELPER(a, b, c) a##b##c
#define METHOD(a, b, c) METHOD_HELPER(a, b, c)

int method_1_16(int x) {
   printf("method_1_16 : %d\n", x);
}

int method_2_16(int x) {
   printf("method_2_16 : %d\n", x);
}

int method_1_32(int x) {
   printf("method_1_32 : %d\n", x);
}

int method_2_32(int x) {
   printf("method_2_32 : %d\n", x);
}

int main() {
   METHOD(method, GROUP_FIRST, TYPE_32);
   METHOD(method, GROUP_SECOND, TYPE_16);
   return 0;
}


Happy hacking!!! :)

วันเสาร์ที่ 1 มีนาคม พ.ศ. 2557

กลับมาหา ภาษาที่คุ้นเคย, C++

ในที่สุดก็ต้องกลับมาภาษาที่คุ้นเคย C/C++ ดีใจได้เขียนแบบจริงๆ จังๆ อีกครั้ง โครงการดีด้วย...

จะว่าไป C/C++ เป็นภาษาเดียวในชีวิตที่ไม่ต้องเปิดคู่มือ (นอกจาก features ใหม่ๆ บางตัวใน C++11)

ทำให้สะท้านเหมือนกัน ตอนเรียน Go (lang) ก็ชอบวิธีการ assignment อย่าง
X := 12 // X เป็น Integer
ใน C++11 ก็มี
auto X = 12; 

ตอนปี 2008 ผมเคยซื้อ Library Qt ตอนนั้น พึ่งจะเป็น Release version 4.0 มีลูกค้าจ้างพัฒนาโปรแกรมสอง Platform ตือ OSX และ Windows ตัดสินใจจ่ายค่า Library ให้กับ Troll ไป เกือบสองแสนบาทสำหรับ สอง Platform 

สถานะ Qt ตอนนี้ มันสุดยอดจริงๆ นอกจากเขียนบน Linux, OSX, Windows ได้แล้ว ยัง Cross compile ไป iOS และ Android ได้อีก 
Android นี่สะดวกกว่าเพื่อน เขียนได้ทั้งบน Linux, OSX และ Windows เลย ส่วน iOS ต้องเขียนบน OSX

ตอนนี้ได้กลับมาใช้อีก ดีจัง (ตังค์อยู่ครบ)

แเละเหมือนเดิมคือ Oracle Call Interface สำหรับ Qt (QOCI) ไม่สามารถใช้ได้ ต้อง Build เอง เพราะต้องไป download OCI Library และรับทราบ License agreement ของ Oracle ก่อน 

วิธี Build QOCI บน OSX

download instanceclient มาจาก Oracle.com ตาม blog ก่อนหน้านี้ http://nanusorn.blogspot.com/2014/02/build-oracle-call-interface-golang.html

เวลา install Qt 5.2.x จะอยู่ที่ ~/Qt5.2.1 ให้ change directory ไปที่ ~/Qt5.2.1/5.2.1/Src/qtbase/src/plugins/sqldrivers/oci

$ export PATH=$PATH;~/Qt5.2.1/5.2.1/clang_64/bin

เรียก qmake สร้าง Makefile ใน folder ~/Qt5.2.1/5.2.1/Src/qtbase/src/plugins/sqldrivers/oci
$ qmake -o Makefile

แก้ Makefile.Release และ Makefile.Debug
โดยเพิ่ม -I/usr/lib/instantclient_11_2/sdk/include ที่ท้ายบรรทัด INCPATH
และ
เพิ่ม LFLAGS        += -L/usr/lib/instantclient_11_2 -lclntsh ใต้บรรทัด LFLAGS

แล้วเรียก 
$ make

วิธีนี้ง่ายสุด เร็วสุด ไม่ต้อง re-build Qt ทั้งตัว...

---------------------------------------------------------------
ถาม : กลับมาเขียน Qt เพื่อ?
ตอบ : เพื่อต้องการใช้ C++ เขียน Consumer สำหรับ rabbitMQ 

ถาม : แค่นี้หรือ?
ตอบ : ป่าวจะเอาไปเขียน Client Application บน Cubieboard ด้วย

ถาม : แล้วอย่างอื่นล่ะ?
ตอบ : ตอนนี้สนใจเอามาใช้พัฒนา Web Application ด้วยนะ เช่น
ตอบจริงๆ : ที่ว่ามาน่ะ ตอบเล่นๆ :p แต่เล่นจริงๆ นะ ปี๊ดส์ เลย