UInt ML_(am_sprintf) ( HChar* buf, const HChar *format, ... ) { UInt ret; va_list vargs; va_start(vargs,format); ret = local_vsprintf(buf, format, vargs); va_end(vargs); return ret; }
int tchar_vsprintf_s_imp(T* buf, size_t nBufCount, const T* format, va_list& v, bool truncate) { T* buf_end=buf+nBufCount; //変換リミット T* dst=buf; //変換先ワーク変数 const T* src=format; //変換元ワーク変数 while(*src){ if(nBufCount!=MAX_BUF && dst>=buf_end-1)break; //書式指定フィールドを取得 if(is_field_begin(*src)){ const T* field_begin=src; src++; src=skip_field_flag(src); src=skip_field_width(src); src=skip_field_precision(src); const T* prefix = src; src=skip_field_prefix(src); if(is_field_type(*src)){ src++; const T* field_end=src; //フィールドを一時変数にコピー T field[64]; if(field_end-field_begin>=_countof(field))field_end=field_begin+_countof(field)-1; //フィールド長制限 auto_strncpy(field,field_begin,field_end-field_begin); field[field_end-field_begin] = 0; //フィールド内に%tsまたは%tcがあったら、適切に変換 field_convert(field); //変換処理は標準ライブラリに委譲 int ret; va_list tmp_v=v; //※vをコピーして用いる if(truncate){ ret=local_vsnprintf_s(dst,buf_end-dst,field,tmp_v); if( ret<0 ){ //バッファに入りきらない文字列が切り捨てられた return -1; } } else if(nBufCount!=MAX_BUF){ ret=local_vsprintf_s(dst,buf_end-dst,field,tmp_v); } else{ ret=local_vsprintf(dst,field,tmp_v); } //vを進める。自信なっしんぐ my_va_forward(v,field, prefix); //変換先ワークポインタを進める if(ret!=-1){ dst+=ret; } src=field_end; } else{ //有効な型フィールドではなかったので、そのまんま出力しちゃう *dst++ = *src++; } } else{ //無変換 *dst++ = *src++; } } //終端 *dst = 0; if( truncate && *src != '\0' ){ //切り詰めありで、srcの処理が完了していない場合 return -1; //切り詰められた } return dst-buf; }