« 買いましたよ♪よつばととエマ! | トップページ | 三鷹市美術ギャラリー 怪獣と美術 »

2007年9月29日 (土)

「OutputDebugString」って…

VC++には、デバッグを支援するために
デバッグウインドウにテキスト情報を出力する
「OutputDebugString」という関数がある。

これが…今一。(汗)

「printf」などのように何でも食ってくれればいいのだが
文字列しか食ってくれない…。

で、勢いこんな物を作る。

#include    <stdio.h>
static void OutputDebugString2( LPSTR format, ... )
{
    va_list            args;
    char            buffer[256];

    va_start( args, format );
    _vsnprintf( buffer, sizeof( Buffer ) - 2, format, args );
    *( LPWORD )( buffer + sizeof( buffer ) - 2 )    = 0;
    OutputDebugString( buffer );
}

最もこれには、元ネタがある!
「Microsoft Visual Studio」内の「Include」の中にある
「DPRINTF.H」に「static void dprintf(char *format, ...)」が元ネタ。

意外に「Include」の中には、小ネタが入っています。(笑)

でもバグ持ちなのでコイツは、修正したもの。
「_vsnprintf」を使用しているのは、入力された
文字列が長すぎてこの処理自体がバグッて
えらい悩まされたから…。<おばかです…。

2バイトの0は、漢字の先行バイトで切れた場合に備えて。
一応これでバグらないはず…。<一応試した。

で、こんな感じで運用!

#ifdef _DEBUG
#define EE( v ) if( v ){char b[5];itoa(__LINE__,b,10);OutputDebugString("*ERROR:"__FILE__":");OutputDebugString(b);OutputDebugString(":"#v);goto EXIT;}
#else
#define EE( v ) if( v ){goto EXIT;}
#endif
int file_read(char*fname,char**fbuffer,size_t*fsize){
    int f=0,r=0,s;
    char *b=NULL;
    EE((f=open(fname,_O_RDONLY|_O_BINARY,0))==-1);
    EE((s=lseek(f,0,2))==0);
    EE(lseek(f,0,0)!=0);
    EE((b=(char*)malloc(s))==NULL);
    EE(read(f,b,s)!=s);
    *fbuffer=b;
    *fsize=s;
    b=NULL;
    r=1;
    EXIT:
    if(b!=NULL)free(b);
    if(f>=0)close(f);
    /*if(!r)printf("err\n");*/
    return r;
}

後処理が共通なので成立・不成立でも
確実に行えるのでミスの軽減が期待できる。
また、処理が停止しない場合でもエラーがアウトプットウインドウに
経過が出力されるので原因の特定がかなり楽になる。

ちなみに「goto EXIT;」を「for(;;);」にすれば、
エラーを出力して処理をストップする。

もし、エラーコードを返すようにしたいのなら…
EE(r=-1,(f=open(fname,_O_RDONLY|_O_BINARY,0))==-1);
なんてのもありかと。

ただエラーコードを一元化すると混乱が少ないけど
一元化するのが難しいし数も膨大になる。

どうしても運用を考えてしまうので
結局単純にエラーを返すようにした。

エラー発生場所は、明確にアウトプットされるしね♪

bool file_read(char*fname,char**fbuffer,size_t*fsize){
    int f=0,r=0,s;
    char *b=NULL;
    EE((f=open(fname,_O_RDONLY|_O_BINARY,0))==-1);
    EE((s=lseek(f,0,2))==0);
    EE(lseek(f,0,0)!=0);
    EE((b=(char*)malloc(s))==NULL);
    EE(read(f,b,s)!=s);
    *fbuffer=b;
    *fsize=s;
    close(f);
    return true;
    EXIT:
    if(b!=NULL)free(b);
    if(f>=0)close(f);
    return false;
}

このマクロでエラーの発生場所が
ダイレクトで表示されるので
デバックがかなり楽になりましたよ♪

|

« 買いましたよ♪よつばととエマ! | トップページ | 三鷹市美術ギャラリー 怪獣と美術 »

コメント

コメントを書く



(ウェブ上には掲載しません)




トラックバック


この記事へのトラックバック一覧です: 「OutputDebugString」って…:

« 買いましたよ♪よつばととエマ! | トップページ | 三鷹市美術ギャラリー 怪獣と美術 »