C标准库中有sprintf和sscan两个函数,可以非常方便的将变量格式化到字符串中,或从字符串中提取数值存放在变量中。
在协议的封装时,如果有函数可以方便的从数值中按指定的格式提取到变量中(协议解析)或从把变量按指定的格式存放在数值中(协议的封包),那将是一件方便的事情。
就我的经验没有见过类似的函数,自己简单实现了一个。欢迎评论和交流。
暂且起个名字叫bprintf和bscan。b (bin或bytearray)
代码如下:
-
*****************************************************************************/
-
* Contact information:
* sites: mailan7749.blog.chinaunix.net
*
* e-mail: mailan2008@qq.com
*****************************************************************************/
-
-
#include <stdarg.h>
-
#include <stdio.h>
-
-
typedef unsigned char INT8U;
-
typedef unsigned short INT16U;
-
typedef unsigned int INT32U;
-
-
/**
-
* @brief 类printf,将变量按指定的格式fmt,存放在buf中。
-
*
-
* @param buf:存放被格式化的数据
-
* @param fmt:格式化字符串
-
*
-
*/
-
char bprintf(INT8U * buf, const char * fmt, ...)
-
{
-
char len;
-
char type;
-
INT8U data_8;
-
INT16U data_16;
-
INT32U data_32;
-
va_list argp;
-
-
if ( (buf == NULL) || (fmt == NULL) )
-
return -1;
-
-
va_start(argp, fmt);
-
while(*fmt != 0)
-
{
-
if (*fmt == ' ')
-
{
-
fmt ++;
-
}
-
else if (*fmt == '%')
-
{
-
len = fmt[1] ;
-
type = fmt[2];
-
if ( type != 'x' )
-
return -1;
-
switch(len)
-
{
-
case '1':
-
data_8 = va_arg(argp, INT8U);
-
*buf++ = data_8;
-
break;
-
case '2':
-
data_16 = va_arg(argp, INT16U);
-
*buf++ = (data_16 >> 8) & 0xFF;
-
*buf++ = data_16 & 0xFF;
-
break;
-
case '4':
-
data_32 = va_arg(argp, INT32U);
-
*buf++ = (data_32 >> 24) & 0xFF;
-
*buf++ = (data_32 >> 16) & 0xFF;
-
*buf++ = (data_32 >> 8) & 0xFF;
-
*buf++ = data_32 & 0xFF;
-
break;
-
default:
-
return -1;
-
break;
-
}
-
fmt += 3;
-
}
-
else
-
{
-
*buf = (INT8U)( (fmt[0] - '0') << 4 ) + ( fmt[1] - '0' );
-
fmt += 2;
-
buf ++;
-
}
-
}
-
va_end(argp);
-
return 0;
-
}
-
-
/**
-
* @brief 类scan,将buf中的数据按指定的格式fmt,存放在变量中。
-
*
-
* @param buf:存放被格式化的数据
-
* @param fmt:格式化字符串
-
*
-
*/
-
char bscan(INT8U * buf, const char *fmt, ...)
-
{
-
void * p;
-
char len;
-
char type;
-
va_list argp;
-
-
if ( (buf == NULL) || (fmt == NULL) )
-
return -1;
-
-
va_start(argp, fmt);
-
while(*fmt != 0)
-
{
-
if (*fmt == ' ')
-
{
-
fmt ++;
-
}
-
else if (*fmt == '%')
-
{
-
len = fmt[1] ;
-
type = fmt[2];
-
if ( type != 'x' )
-
return -1;
-
switch(len)
-
{
-
case '1':
-
p = va_arg(argp, void *);
-
*(INT8U *)(p) = *(INT8U *)buf++;
-
break;
-
case '2':
-
p = va_arg(argp, void *);
-
*(INT16U *)(p) = *(INT16U *)buf;
-
buf += 2;
-
break;
-
case '4':
-
p = va_arg(argp, void *);
-
*(INT32U *)(p) = *(INT32U *)buf;
-
buf += 4;
-
break;
-
default:
-
return -1;
-
break;
-
}
-
fmt += 3;
-
}
-
else
-
{
-
fmt += 2;
-
buf ++;
-
}
-
}
-
va_end(argp);
-
return 0;
-
}
-
-
void main( void )
-
{
-
INT8U buf[20];
-
INT8U a = 1;
-
INT32U b = 2;
-
INT32U c1;
-
INT8U c2;
-
INT8U c3;
-
bprintf(buf, "12 34 56 78 %1x %1x 55", a, b);
-
bscan(buf, "%4x %1x %1x", &c1, &c2, &c3);
-
}
阅读(3095) | 评论(0) | 转发(0) |