2006年04月

2006年04月25日

Windowsで外部入力ポートを使う

玄関の施錠状態を携帯から確認する為にWEBサーバ上のアプリから外部ポートのon/off信号を読む。
サーバに使うノートパソコンのRS232Cを読み込み用に使う。
ポートの読み込みにはGetCommModemStatus()を使う。


/** rs232c.h */
class RS232C
{
public:
	int CurrentComNum;
	DCB dcb;
	volatile HANDLE hCom;
	HWND hWnd;

	RS232C();
	~RS232C();

	bool Init(int ComNum, HWND hPWnd, char *parm = "baud=9600 parity=N data=8 stop=1");
	bool ComOpen(int ComNum);
	bool ComClose();
	bool SetFunction(DWORD func);
	bool Select(int ComNum);
	bool GetLine(DWORD Mask);
};

/** rs232c.cpp */


RS232C *prs232c;

//
//コンストラクタ
//
RS232C::RS232C()
{
	CurrentComNum = 0;
	hWnd = 0;
	hCom = NULL;
	prs232c = this;
}

//
//
RS232C::~RS232C()
{
	ComClose();
}
//
// COMポートを開く
//
bool RS232C::Init(int ComNum, HWND hPWnd, char *param)
{
	if(false == ComOpen(ComNum))
	{
		MessageBox(NULL, "Comポートは使えません","Com Open Error", MB_OK);
		return false;
	}
	hWnd = hPWnd;
	return true;
}

//
// COMポートを閉じる
//
bool RS232C::ComClose()
{
	if(hCom == NULL)
		return true;
	CurrentComNum = 0;
	return CloseHandle(hCom)==TRUE?true:false;
}

//
// COMポートを開く
//
bool RS232C::ComOpen(int ComNum)
{
	char buff[256];
	sprintf(buff, "COM%d", ComNum);
	//COMポートを開く
	hCom = CreateFile(buff, GENERIC_READ| GENERIC_WRITE, 0, NULL, OPEN_EXISTING, NULL, NULL);
	if(hCom == INVALID_HANDLE_VALUE){
		hCom = NULL;
		return false;
	}
	CurrentComNum = ComNum;

	//タイマー設定
	COMMTIMEOUTS Timeout;
	Timeout.ReadIntervalTimeout = 0;
	Timeout.ReadTotalTimeoutMultiplier = 0;
	Timeout.ReadTotalTimeoutConstant = 0;
	Timeout.WriteTotalTimeoutMultiplier = 10;
	Timeout.WriteTotalTimeoutConstant = 100;
	SetCommTimeouts(hCom, &Timeout);

	//通信設定
	DCB Dcb;
	GetCommState(hCom, &Dcb);
	Dcb.BaudRate = CBR_19200;
	Dcb.ByteSize = 8;
	Dcb.Parity = NOPARITY;
	Dcb.StopBits = ONESTOPBIT;
	SetCommState(hCom, &Dcb);

	return true;
}

//
// CLRDTR,SETDTR, CLRRTS,SETRTS
//
bool RS232C::SetFunction(DWORD func)
{
	if(hCom == NULL)
		return false;
	return EscapeCommFunction(hCom, func) == TRUE?true:false;
}

//
// 開いているCOMポートを閉じて
// COMポートを開く
//
bool RS232C::Select(int ComNum)
{
	SetCommMask(hCom, 0);
	CloseHandle(hCom);
	if(false == ComOpen(ComNum))
	{
		MessageBox(NULL, "COMポートはつかえません", "", MB_OK);
		ComOpen(CurrentComNum);
	}
	else
	{
		CurrentComNum = ComNum;
	}
	return true;
}

//
// COMポートの状態を取得する 
//
bool RS232C::GetLine(DWORD Mask)
{
	DWORD ModemStatus;
	if(FALSE == GetCommModemStatus(hCom, &ModemStatus))
		return false;
	return (ModemStatus & Mask)?true: false;
}


2006年04月06日

RUNDLL32とVXWORKSとPRINTUI3

プリンタドライバのインストーラではprintui.dllの関数をバッチファイルから呼び出していますが、DLL内の関数を直接呼び出すツールとしてrundll32.exeがあります。
コマンドプロンプトからPrintUIEntryを呼び出す場合以下の様に引数を入力します。
>rundll32 printui,PrintUIEntry /?
/?を指定するとヘルプ表示になり使える引数が表示されます。
インストール、アンインストール、テストプリントをバッチで起動するのに便利なインターフェースが用意されています。
ただ惜しいことにローカルポートを作成するインターフェースがありません。
tcp/ipのポートは別の方法で作成できるようですがローカルポートには適用されないようです。
その為にPRTGRAPHのインストーラではポートの追加が手動になっています。


vxworksはりアルタイムOSですが、rundll32より更に面白い事に起動しているプロセス内の任意の関数が呼び出せるようになっています。
これにより他のOSではデバッガを起動してメモリや変数を参照するような事がデバッガ無しで可能で、更に特定の処理をコマンドラインから割り込ませる事も出来てしまいます。火星探査機にもvxworksが使われているとの事です。
http://ja.wikipedia.org/wiki/VxWorks



2006年04月01日

JPEG変換プリンタドライバ3

http://www.ksky.ne.jp/~yamama/prtgraph/index.htm
プリンタドライバPRTGRAPHとは
WORDやEXCEL、InternetExploret等の印刷機能の付いたアプリケーションからPRTGRAPHに印刷を行う事でJPEGファイル形式に変換しファイルを作成するプリンタドライバです。プリンタに印刷可能な文書・図面であれば印刷イメージでJPEGファイルに変換できます。
これはテストページ印刷のJPEG変換ファイル
テストページのJPEG