&]部分类型的冲突"由于GCC 4.8.2宏定义 [英] "Section type conflict" due to macro definition in GCC 4.8.2

查看:401
本文介绍了&]部分类型的冲突"由于GCC 4.8.2宏定义的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我得到一个部分类型的冲突,如果我调用内联函数的宏。
没有什么可以对这个错误在WWW上找到。

I get a "section type conflict" if I call a macro in an inlined function. There is nothing which can be found about this error in the WWW.

宏的目的是提供一个宏来处理保存在闪光灯的Arduino(只是一个辅助信息)的字符串。
如果函数不是内联的一切都很好。可能是什么原因呢?

The intention of the macro is to offer a macro to deal with strings saved in the flash for Arduino (just a side info). If the function is not inlined everything is fine. What may be the reason?

#undef PROGMEM
#define PROGMEM __attribute__(( section(".progmem.data") ))

#undef PSTR
/* need to define prog_char in avr-gcc 4.7 */
#if __AVR__ && __GNUC__ == 4 && __GNUC_MINOR__ > 6
typedef char prog_char;
#endif
/* Need const type for progmem - new for avr-gcc 4.6 */
#if __AVR__ && __GNUC__ == 4 && __GNUC_MINOR__ > 5
#define PSTR(s) (__extension__({static const prog_char __c[] PROGMEM = (s); \
                                  (const prog_char_t *)&__c[0]; }))
#else
#define PSTR(s) (__extension__({static prog_char __c[] PROGMEM = (s); \
                                  (prog_char_t *)&__c[0]; }))
#endif

code:

inline void test() {
    hal.console->println("AP_Common tests\n");
    hal.console->println_P(PSTR("AP_Common tests\n") );
    hal.console->printf_P(PSTR("AP_Common tests\n") );
}

void setup(void)
{
  test();
}

void loop(void)
{
    // do nothing
}

误差:println_P(PSTR(坏VAR表\\ n));

Errors for: "println_P(PSTR("Bad var table\n") );"

AP_HAL/utility/BetterStream.h:53:57: note: in definition of macro 'printf_P'
 #define printf_P(fmt, ...) _printf_P((const prog_char *)fmt, ## __VA_ARGS__)
                                                         ^
output_debug.h:13:26: note: in expansion of macro 'PSTR'
   hal.console->printf_P( PSTR("{\"t\":\"s_cmp\",\"h\":%.1f}\n"),
                          ^
AP_Progmem/AP_Progmem_AVR.h:25:56: note: '__c' was declared here
 #define PSTR(s) (__extension__({static const prog_char __c[] PROGMEM = (s); \
                                                        ^
AP_HAL/utility/BetterStream.h:53:57: note: in definition of macro 'printf_P'
 #define printf_P(fmt, ...) _printf_P((const prog_char *)fmt, ## __VA_ARGS__)
                                                         ^
AP_test.ino:60:27: note: in expansion of macro 'PSTR'

修改

在派生类两次调用PSTR()会导致相同的问题。
我认为这是一个编译器缺陷,从而导致未定义的行为。

Calling PSTR() in two times derived classes causes the same problem. I think it is a compiler bug, which leads to undefined behavior.

推荐答案

尝试: PROGMEM静态常量prog_char __c [] 。奇怪的是,我发现该属性必须preceed申报不知道您的版本实际上没有。这很可能是这个问题。

try: PROGMEM static const prog_char __c[]. Strange is, that I found out the attribute must preceed the declaration Not sure what your version actually does. This might very well be the problem.

或者:该段的类型是向locical存储器部分中的值存储的属性。我想这是报告的链接。该PROGMEM部分默认NOLOAD(这是有道理的,本节)。然而,由于在初始化过程中,编译器要求的部分是相对的,从而导致错误。即使事实并非如此,我就搜索问题在该区域。

Alternatively: The section type is an attribute to the locical memory section the values are stored. I suppose this was reported by the linker. the PROGMEM section is NOLOAD by default (which is makes sense for this section). However, due to the initialization, the compiler requires the section to be the opposite, thus resulting in the error. Even if that is not true, I would search the problem in this area.

一些附加备注:


  • 使用stdint类型,不要依赖于内置类型它们的大小。

  • 小心'字符。只使用实际字符,不依靠他们签署的烦躁。如果你有关心不同类型(uint8_t有或中int8_t)会更合适。

  • `和#undef'宏不大,但是的后,他们的使用前的如果需要的话。否则,一个意想不到的重新定义可能不通过一个警告。这些错误可能很难调试!在标题中使用,而不是后卫。

  • 在微控制器的常量-正确性的是至关重要的,所以明智地使用它。做的不可以避免常量即使这需要更多的努力(直到你获得更多的经验)。这不仅会在编译时检测到共同的缺陷,同时也节省了内存和(甚至可能)Flash作为非const变量存储在RAM在Flash初始化值。

  • 请不要使用 __ - 在custon code prefixes。这些应保留工具链的编译器和库系统)。你可以使用这个作为后缀,虽然(但为什么在这个例子?)

  • 避免类型转换。在初学者的code大多数的演员其实是不必要或不好的界面设计的症状。基本上是:如果你没有指定一个参数传递给函数的类型,不应该要求一个类型转换。 (是的,有产生的异常 - 这就是为什么我把它叫做一个基本的规则,而不是法律)

  • 在一般:使用所有的帮助编译器就可以得到。嵌入式调试是不是很有趣。

  • use stdint types, do not rely on the built-in types for their size.
  • Be careful with 'char'. Use only for actual characters and do not rely on their signed-ness. If you have to care about a different type (uint8_t or int8_t) would be more appropriate.
  • `#undef' macros not before their usage, but after if necessary. Otherwise, an unintended redefinition might pass without a warning. These errors can be very hard to debug! Use guards in headers instead.
  • In microcontrollers, const-correctness is vital, so use it wisely. Do not avoid const even if this takes more effort (until you get more experience). This will not only detect common flaw at compile-time, but also saves RAM and (possibly even) Flash as non-const variables are stored in RAM with initialization values in Flash.
  • Do not use __-prefixes in custon code. These should be reserved for the compiler and system libs of the toolchain). You might use this as suffix, though (but why in the example??)
  • Avoid typecasts. Most casts in beginner's code are actually unnecessary or a symptom of bad interface design. Basically: if you do not have to specify the type of an argument to a function, a typecast should not be required. (Yes, there are exeptions - that's why I call it a basic rule, not a law).
  • In general: use all help from the compiler you can get. Embedded debugging is not really fun.

这篇关于&]部分类型的冲突"由于GCC 4.8.2宏定义的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆