[STM8] 国sscan()中用不到%d格式

[复制链接]
5464|15
 楼主| gjz175 发表于 2011-11-7 14:23 | 显示全部楼层

IAR中用函数sscanf()的问题

static char SG[30];
  static char RxCounter = 0;
  char* ptr;

   ptr = SG;
   sscanf(ptr, "%d", &RxCounter);    // SG=“67 ”
   这样写说参数的格式不对。

    sscanf(ptr, "%d", &RxCounter);中的%d改为%s后,没有警告,可以在变量中保存'6'。
    在帮助文档中说明可以用%d的格式的,要怎样才能正确使用呢?
 楼主| gjz175 发表于 2011-11-7 14:26 | 显示全部楼层
补充:在option中Scanf formatting 已经选择为Full
 楼主| gjz175 发表于 2011-11-7 14:57 | 显示全部楼层
什么在IAR中,sscan()中用不到%d格式,用%s没问题?
 楼主| gjz175 发表于 2011-11-7 14:57 | 显示全部楼层 |阅读模式
本帖最后由 gjz175 于 2011-11-7 16:46 编辑

为什么在IAR中,sscan()中用不到%d格式,用%s没问题?
 楼主| gjz175 发表于 2011-11-7 15:23 | 显示全部楼层
怎么都 只看不回啊?
 楼主| gjz175 发表于 2011-11-7 16:19 | 显示全部楼层
本帖最后由 gjz175 于 2011-11-7 16:54 编辑

以下程序,在TC中正常运行。在IAR中,警告参数不兼容,最后结果不正确。
warming[]:argument is incompatible with corresponding format string conversion
求大侠帮忙

   char SG[4];   
    char RxCounter = 0;
   char* ptr;
   SG[0]='1';
   SG[1]='1';
   SG[2]='3';
   SG[3]='d';
   ptr = SG;

   sscanf(ptr, "%d",&RxCounter);
    printf("RxCounter = %d.",RxCounter);
 楼主| gjz175 发表于 2011-11-7 16:21 | 显示全部楼层
以上程序,在TC中正常运行。在IAR中,警告参数不兼容,最后结果不正确。
求大侠帮忙
 楼主| gjz175 发表于 2011-11-7 17:05 | 显示全部楼层
自己顶。等待。。。
香水城 发表于 2011-11-7 17:05 | 显示全部楼层
把 & 去掉。
hgjinwei 发表于 2011-11-7 21:47 | 显示全部楼层
char RxCounter;
"%d",&RxCounter ?
不怕内存越界啊?

评分

参与人数 1威望 +1 收起 理由
gjz175 + 1

查看全部评分

pkat 发表于 2011-11-7 22:48 | 显示全部楼层
把 & 去掉试试
 楼主| gjz175 发表于 2011-11-8 08:49 | 显示全部楼层
把&去掉验证了,是不行的。help手册有说要加“&”,而且也有说支持%d的格式。
6楼的程序在TC上运行是正常的,即从字符串中读数,以十进制保存在RxCounter中。
hgjinwei 发表于 2011-11-8 13:21 | 显示全部楼层
你所说的在TC上运行正常,是否是以Debug模式编译的,下面这段代码在VS2005上测试。
问题出在 RxCounter 的类型上,RxCounter 为char 型,但scanf会将他认为是int型,
然后就内存越界了。
还有,printf("RxCounter = %d.",RxCounter); 在8位机中也有可能出错,原因一样,
不过是读越界。但32位机没有表现出异常,可能是传参方式造成的,没有仔细查看过。

IAR还挺强悍的啊,这样也报错,不错。

  1. #include "stdint.h"
  2. #include <stdio.h>


  3. void mputs(int len,void *pdat)
  4. {
  5.     int i;
  6.     unsigned char *sp = (unsigned char *)pdat;

  7.     for(i=0; i<len; ){
  8.         int tmp = *(sp+i);
  9.         printf("%02X ",tmp);
  10.         
  11.         if(0 == (++i%8)){
  12.             printf("\r\n");
  13.         }
  14.     }
  15. }

  16. int main(int argc, char *argv[])
  17. {
  18.     char    ch1 = 0x11;
  19.     char    ch2 = 0x12;
  20.     char    buff[4] = {0xA0,0xA1,0xA2,0xA3};

  21.     struct {
  22.         char    ch1;
  23.         char    ch2;
  24.         char    buff[4];
  25.     }mm = {
  26.         0x21,
  27.         0x22,
  28.         0xB0,0xB1,0xB2,0xB3
  29.     };

  30.     printf("\r\nroom ch1  @ 0x%08X : ",(unsigned long)&ch1);
  31.     mputs(sizeof(int),&ch1);
  32.     printf("\r\nroom ch2  @ 0x%08X : ",(unsigned long)&ch2);
  33.     mputs(sizeof(int),&ch2);
  34.     printf("\r\nroom buff @ 0x%08X : ",(unsigned long)&buff[0]);
  35.     mputs(sizeof(int),&buff[0]);

  36.     printf("\r\nroom mm   @ 0x%08X : ",(unsigned long)&mm);
  37.     mputs(sizeof(mm),&mm);
  38.     printf("\r\n");

  39.     // 输入字符到ch1,因为编译器在分配空间时有可能强制了地址对齐,所以有可能不会影响到ch2
  40.     // PS VS2005中在Debug模式编译时,ch1的输入不会干扰ch2,编译器预留了变量监测空间,但在
  41.     // Release模式编译时,ch1的输入干扰了ch2。
  42.     printf("input char to ch1 : ");
  43.     scanf("%d",&ch1);

  44.     // 输入字符到mm.ch1,因为我们已经限定了mm.ch1及mm.ch2的分布,且均为char格式,符合编译器
  45.     // 的对齐要求,mm.ch2将受mm.ch1输入的干扰而变化。
  46.     printf("input char to mm.ch1 : ");
  47.     scanf("%d",&mm.ch1);

  48.     printf("\r\nroom ch1  @ 0x%08X : ",(unsigned long)&ch1);
  49.     mputs(sizeof(int),&ch1);
  50.     printf("\r\nroom ch2  @ 0x%08X : ",(unsigned long)&ch2);
  51.     mputs(sizeof(int),&ch2);
  52.     printf("\r\nroom buff @ 0x%08X : ",(unsigned long)&buff[0]);
  53.     mputs(sizeof(int),&buff[0]);

  54.     printf("\r\nroom mm   @ 0x%08X : ",(unsigned long)&mm);
  55.     mputs(sizeof(mm),&mm);
  56.     printf("\r\n");

  57.     getch();
  58. }
 楼主| gjz175 发表于 2011-11-8 13:43 | 显示全部楼层
看你的回复之前,先谢你的详细解答。
 楼主| gjz175 发表于 2011-11-8 14:05 | 显示全部楼层
再谢谢你,因为问题解决了。
定义为int型后,问题就解决了。
 楼主| gjz175 发表于 2011-11-8 14:12 | 显示全部楼层
总结一下:

    函数的原型是:​​int sscanf(const char *restrict s, const char *restrict format, ...);


    函数printf("RxCounter = %d.",RxCounter);

  RxCounter定义的类型                  结果

    int8_t、uint8_t                    警告并不能运行

    int 、uint16_t                      无警告正确运行

    int16_t、int32_t、uint32_t   警告但能够正确运行


即RxCounter长度小于8位是不能正确运行的,hgjinwei说得对。谢谢hgjinwei的详细解答
您需要登录后才可以回帖 登录 | 注册

本版积分规则

0

主题

45

帖子

1

粉丝
快速回复 在线客服 返回列表 返回顶部