tag 标签: scons

相关博文
  • 热度 3
    2020-9-10 14:49
    3966 次阅读|
    2 个评论
    1. 更改默认环境变量 使用scons编译时,RTT_CC环境变量用于标识编译时使用的工具链,默认配置使用gcc,如果需要修改为iar,则可以编辑文件env_released_1.2.0\env\tools\ConEmu\ConEmu\CmdInit.cmd,找到set RTT_CC=gcc项,将gcc改为iar即可 2. 为STM32F733移植rtconfig.py,支持GCC/IAR/KEIL编译,支持硬件浮点,注意STM32F733的FPU为fpv5-sp-d16,详细可参考链接 https://www.keil.com/support/docs/3716.htm https://www.keil.com/support/man/docs/ARMCC/ARMCC_chr1359124920656.htm https://developer.arm.com/documentation/dui0472/k/Compiler-Coding-Practices/Processors-and-their-implicit-Floating-Point-Units--FPUs- --------------------------------------------------------------------------------------------------------------- import os # toolchains options ARCH='arm' CPU='cortex-m7' CROSS_TOOL='iar' if os.getenv('RTT_CC'): CROSS_TOOL = os.getenv('RTT_CC') if os.getenv('RTT_ROOT'): RTT_ROOT = os.getenv('RTT_ROOT') # cross_tool provides the cross compiler # EXEC_PATH is the compiler execute path, for example, CodeSourcery, Keil MDK, IAR if CROSS_TOOL == 'gcc': PLATFORM = 'gcc' EXEC_PATH = r'/usr/local/Cellar/arm-none-eabi-gcc/7-2017-q4-major/gcc/bin/' elif CROSS_TOOL == 'keil': PLATFORM = 'armcc' EXEC_PATH = r'C:/Keil_v5' elif CROSS_TOOL == 'iar': PLATFORM = 'iar' EXEC_PATH = r'C:/Program Files (x86)/IAR Systems/Embedded Workbench 8.3' if CROSS_TOOL == 'gcc' and os.getenv('RTT_EXEC_PATH'): EXEC_PATH = os.getenv('RTT_EXEC_PATH') BUILD = 'debug' if PLATFORM == 'gcc': # toolchains PREFIX = 'arm-none-eabi-' CC = PREFIX + 'gcc' CXX = PREFIX + 'g++' AS = PREFIX + 'gcc' AR = PREFIX + 'ar' CXX = PREFIX + 'g++' LINK = PREFIX + 'gcc' TARGET_EXT = 'elf' SIZE = PREFIX + 'size' OBJDUMP = PREFIX + 'objdump' OBJCPY = PREFIX + 'objcopy' STRIP = PREFIX + 'strip' DEVICE = ' -mcpu=Cortex-M7 -mthumb -mfpu=fpv5-sp-d16 -mfloat-abi=hard -ffunction-sections -fdata-sections' CFLAGS = DEVICE + ' -g -Wall' AFLAGS = ' -c' + DEVICE + ' -x assembler-with-cpp -Wa,-mimplicit-it=thumb ' LFLAGS = DEVICE + ' -Wl,--gc-sections,-Map=rtthread_gcc.map,-cref,-u,Reset_Handler -T board/linker_scripts/link.lds' CPATH = '' LPATH = '' if BUILD == 'debug': CFLAGS += ' -O0 -gdwarf-2' AFLAGS += ' -gdwarf-2' else: CFLAGS += ' -O2 -Os' CXXFLAGS = CFLAGS POST_ACTION = OBJCPY + ' -O binary $TARGET rtthread_gcc.bin \n' + SIZE + ' $TARGET \n' POST_ACTION += OBJCPY + ' -O ihex $TARGET rtthread.hex \n' POST_ACTION += 'cp rtthread.hex d:\Shared \n' # module setting CXXFLAGS = ' -Woverloaded-virtual -fno-exceptions -fno-rtti ' M_CFLAGS = CFLAGS + ' -mlong-calls -fPIC ' M_CXXFLAGS = CXXFLAGS + ' -mlong-calls -fPIC' M_LFLAGS = DEVICE + CXXFLAGS + ' -Wl,--gc-sections,-z,max-page-size=0x4' +\ ' -shared -fPIC -nostartfiles -static-libgcc' M_POST_ACTION = STRIP + ' -R .hash $TARGET\n' + SIZE + ' $TARGET \n' elif PLATFORM == 'armcc': # toolchains CC = 'armcc' CXX = 'armcc' AS = 'armasm' AR = 'armar' LINK = 'armlink' TARGET_EXT = 'axf' DEVICE = ' --cpu Cortex-M7.fp.sp --fpu=FPv5-SP' CFLAGS = DEVICE + ' --c99 --split_sections --apcs=interwork ' AFLAGS = DEVICE + ' --apcs=interwork ' LFLAGS = DEVICE + ' --apcs=interwork --summary_stderr --info summarysizes --map --xref --callgraph --symbols --info sizes --info totals --info unused --info veneers --list rtthread_keil.map --scatter board/linker_scripts/link.sct --strict' CFLAGS += ' -I' + EXEC_PATH + '/ARM/ARMCC/include' LFLAGS += ' --libpath "' + EXEC_PATH + '/ARM/ARMCC/lib"' EXEC_PATH += '/ARM/ARMCC/bin' if BUILD == 'debug': CFLAGS += ' -g -O0' AFLAGS += ' -g' else: CFLAGS += ' -O2 -Otime' CXXFLAGS = CFLAGS POST_ACTION = 'fromelf --bin $TARGET --output rtthread_keil.bin \n fromelf -z $TARGET \n' POST_ACTION += 'fromelf --i32combined $TARGET --output rtthread.hex \n' POST_ACTION += 'cp rtthread.hex d:\Shared \n' elif PLATFORM == 'iar': # toolchains CC = 'iccarm' CXX = 'iccarm' AS = 'iasmarm' AR = 'iarchive' LINK = 'ilinkarm' TARGET_EXT = 'out' DEVICE = '' CFLAGS = DEVICE CFLAGS += ' --diag_suppress Pa050' CFLAGS += ' --no_cse' CFLAGS += ' --no_unroll' CFLAGS += ' --no_inline' CFLAGS += ' --no_code_motion' CFLAGS += ' --no_tbaa' CFLAGS += ' --no_clustering' CFLAGS += ' --no_scheduling' # CFLAGS += ' --debug' CFLAGS += ' --endian=little' CFLAGS += ' --cpu=Cortex-M7.fp.sp' CFLAGS += ' -e' CFLAGS += ' --fpu=VFPv5_sp' CFLAGS += ' --dlib_config "' + EXEC_PATH + '/arm/INC/c/DLib_Config_Normal.h"' CFLAGS += ' --use_c++_inline' CFLAGS += ' --silent' AFLAGS = '' AFLAGS += ' -s+' AFLAGS += ' -w+' AFLAGS += ' -r' AFLAGS += ' --cpu Cortex-M7.fp.sp ' AFLAGS += ' --fpu VFPv5_sp' AFLAGS += ' -S' if BUILD == 'debug': # CFLAGS += ' -Ol' CFLAGS += ' --debug' CFLAGS += ' -On' else: CFLAGS += ' -Oh' LFLAGS = ' --config board/linker_scripts/link.icf' LFLAGS += ' --redirect _Printf=_PrintfTiny' LFLAGS += ' --redirect _Scanf=_ScanfSmall' LFLAGS += ' --entry __iar_program_start' # LFLAGS += ' --silent' CXXFLAGS = CFLAGS EXEC_PATH = EXEC_PATH + '/arm/bin/' POST_ACTION = 'ielftool --bin $TARGET rtthread_iar.bin \n' POST_ACTION += 'ielftool --ihex $TARGET rtthread.hex \n' POST_ACTION += 'cp rtthread.hex d:\Shared \n' def dist_handle(BSP_ROOT, dist_dir): import sys cwd_path = os.getcwd() sys.path.append(os.path.join(os.path.dirname(BSP_ROOT), 'tools')) from sdk_dist import dist_do_building dist_do_building(BSP_ROOT, dist_dir) ---------------------------------------------------------------------------------------------------------------
  • 热度 31
    2015-3-26 22:53
    17451 次阅读|
    1 个评论
           scons的构建文件名称是统一的都称为SConstruct。其是scons所接受的编译脚本主文件。当然为了方便目录的组织,也允许在各个目录下面存放SConscript, 然后最上面SConstruct收集这些SConscript组织成为一个大的构建文件。       这里以bsp/stm32f10x为例予以介绍,其SConstruct文件为:       注: 对于RT-Thread的BSP下的SConstruct文件来说,此文件有些共同的部分。共同部分已高亮为红色。 import os import sys import rtconfig   if os.getenv('RTT_ROOT'):     RTT_ROOT = os.getenv('RTT_ROOT') else:     RTT_ROOT = os.path.normpath(os.getcwd() + '/../..')   sys.path = sys.path + from building import *  注释:RTT_ROOT即代表了RT-Thread源码包的路径,以我的系统为例,我将RT-Thread源码解压到D:\rt-thread\下,则上面代码就会设定RTT_ROOT = 'D:\rt-thread\'   TARGET = 'rtthread-stm32.' + rtconfig.TARGET_EXT  注释:这一句用来设定编译生成的可执行文件的名称,比如是hex,bin或者是elf,还是axf(MDK编译器生成的具有调试信息的可执行文件名称,跟gcc下的elf类似,兼容) rtconfig.TARGET_EXE是指在rtconfig.py中定义的TARGET_EXT,在rtconfig.py中,可以看到有多个TARGET_EXT定义,其含义为目标文件的扩展名。 当TARGET_EXT为'axf'时,最后就会生成的文件为'rtthread-stm32.axf'     env = Environment(tools = , AS = rtconfig.AS, ASFLAGS = rtconfig.AFLAGS, CC = rtconfig.CC, CCFLAGS = rtconfig.CFLAGS, AR = rtconfig.AR, ARFLAGS = '-rc', LINK = rtconfig.LINK, LINKFLAGS = rtconfig.LFLAGS) env.PrependENVPath('PATH', rtconfig.EXEC_PATH)   if rtconfig.PLATFORM == 'iar': env.Replace(CCCOM = ) env.Replace(ARFLAGS = ) env.Replace(LINKCOM = )   Export('RTT_ROOT') Export('rtconfig')   # prepare building environment objs = PrepareBuilding(env, RTT_ROOT)  注释: PrepareBuilding是一个python函数,它是在tools/目录下的脚本文件中定义的,其作用正如其名所示,用于完成编译前的准备工作。   # STM32 firemare library building script objs = objs + SConscript( GetCurrentDir() + '/Libraries/SConscript', variant_dir='build/bsp/Libraries', duplicate=0)  注释:能够让一个SConstruct文件再关联一个新的组件(用户自行定义的组件,而不是RT-Thread系统的组件,此处是STM32的固件库)。 这里SConscript函数SCons内置的函数,它可以读入一个新的SConscript文件,并将SConscript文件中所指明的源码加入编译列表中来。 SConscript文件和下节的组件编译文件实际是一样的,因为可以把BSP看成一个组件Group(在工程文件中它也确实是一个Group),所以这个组件所对应的编译脚本就是SConscript。 SConscript函数的参数包括三个: 第一个是SConscript路径,GetCurrentDir()返回当前文件所处的路径,即SConstruct文件所在的目录,可以看到此目录下存在一个Libraries目录,并且其目录下存在一个SConscript文件,我们将子下一节介绍SConscript文件是介绍它。 variant_dir则指定生成的目标文件的存放路径,这里即为'build/bsp/Libraries',用户当然可以根据自己的喜好做修改。 duiplicate 的作用是设定是否拷贝或链接源文件到variant_dir   if GetDepend('RT_USING_RTGUI'):     objs = objs + SConscript(RTT_ROOT + '/examples/gui/SConscript', variant_dir='build/examples/gui', duplicate=0)  注释:上述代码的意思是,如果在rtconfig.h中定义了宏RT_USING_RTGUI,那么就执行SConscript函数,将rt-thread/examples/gui下的C源码加入编译。 GetDepend函数是python函数,在tools/目录下的脚本文件中定义,它会从rtconfig.h文件读取组件配置信息,其参数为rtconfig.h中的宏名。   # build program  env.Program(TARGET, objs)   # end building  EndBuilding(TARGET)     全部代码: import os import sys import rtconfig   if os.getenv('RTT_ROOT'):     RTT_ROOT = os.getenv('RTT_ROOT') else:     RTT_ROOT = os.path.normpath(os.getcwd() + '/../..')   sys.path = sys.path + from building import *   TARGET = 'rtthread-stm32.' + rtconfig.TARGET_EXT   env = Environment(tools = , AS = rtconfig.AS, ASFLAGS = rtconfig.AFLAGS, CC = rtconfig.CC, CCFLAGS = rtconfig.CFLAGS, AR = rtconfig.AR, ARFLAGS = '-rc', LINK = rtconfig.LINK, LINKFLAGS = rtconfig.LFLAGS) env.PrependENVPath('PATH', rtconfig.EXEC_PATH)   if rtconfig.PLATFORM == 'iar': env.Replace(CCCOM = ) env.Replace(ARFLAGS = ) env.Replace(LINKCOM = )   Export('RTT_ROOT') Export('rtconfig')   # prepare building environment objs = PrepareBuilding(env, RTT_ROOT)   # STM32 firemare library building script objs = objs + SConscript( GetCurrentDir() + '/Libraries/SConscript', variant_dir='build/bsp/Libraries', duplicate=0)   if GetDepend('RT_USING_RTGUI'):     objs = objs + SConscript(RTT_ROOT + '/examples/gui/SConscript', variant_dir='build/examples/gui', duplicate=0)   # build program  env.Program(TARGET, objs)   # end building  EndBuilding(TARGET) 参考资料来源:http://www.rt-thread.org/
  • 热度 18
    2015-3-26 22:53
    24112 次阅读|
    0 个评论
    SConscript文件是用来指定哪些文件会加入编译。先来分析下BSP主目录下的SConscript文件: import rtconfig Import('RTT_ROOT') from building import *   src_bsp = src_drv =   if GetDepend('RT_USING_DFS'): if rtconfig.STM32_TYPE == 'STM32F10X_HD': src_drv += else: src_drv +=   if GetDepend('RT_USING_LWIP'): src_drv += +   if GetDepend('RT_USING_RTGUI'):     src_drv +=   if GetDepend('RT_USING_RTGUI'): if rtconfig.RT_USING_LCD_TYPE == 'FMT0371': src_drv += elif rtconfig.RT_USING_LCD_TYPE == 'ILI932X': src_drv += elif rtconfig.RT_USING_LCD_TYPE == 'SSD1289': src_drv +=   src = src_bsp + src_drv CPPPATH = CPPDEFINES = , CPPPATH = CPPPATH, CPPDEFINES = CPPDEFINES)   Return('group')     GetCurrentDir函数可以获得当前SConscript文件所在的目录。所以使用这个也能够方便的把一个组件的目录包含到工程的头文件搜索路径中。 DefineGroup用于定义一个组件。组件可以是一个目录(下的文件或子目录),也是后续一些IDE工程文件中的一个Group或文件夹。 函数原型为: DefineGroup(name, src, depend, **parameters),包括四个参数: 'name'来定义这个group的名字 src用于定义这个Group中包含的文件,一般指的是C/C++源文件。方便起见,也能够通过Glob函数采用通配符的方式列出SConscript文件所在目录中匹配的文件。 depend 用于定义这个Group编译时所依赖的选项(例如finsh组件依赖于RT_USING_FINSH宏定义)。编译选项一般指rtconfig.h中定义的RT_USING_xxx宏。当在rtconfig.h配置文件中定义了相应宏时,那么这个Group才会被加入到编译环境中进行编译。如果依赖的宏并没在rtconfig.h中被定义,那么这个Group将不会被加入编译。相类似的,在使用scons生成为IDE工程文件时,如果依赖的宏未被定义,相应的Group也不会在工程文件中出现。 parameters则可以输入一组字符串,后面还可以加入的参数包括:           CCFLAGS – C源文件编译的参数;           CPPPATH – 应该额外包含的头文件路径;           CPPDEFINES – C源文件编译时额外的宏定义;           LINKFLAGS – 连接时应该添加的参数。           LIBRARY – 包含此参数,则会将组生成的目标文件打包成库文件。   参考资料来源:http://www.rt-thread.org/