Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: вопросы по scons
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > GNU/OpenSource средства разработки для avr/arm/mips
umup
создал Sconscript :

Код
import os

env = Environment(ENV = os.environ, tools=['mingw'])
env['ENV']['PATH'] = 'c:\\gcc\\win32\\bin;' + os.environ['PATH']

env.Object(source = 'test_01.c', target = 'out/test_01.o')
env.Program(source = 'out/test_01.o', target = 'out/test_01.exe')


1) как одним параметром указать, в какую папку должны помещаться выходные файлы (чтобы не замусоривать папку с исходниками - нужно скомпилировать в локальную папку out/) ?

2) как заставить scite показать вывод из gcc ?

добавил в cpp.properties :
command.build.*.c=scons.py

компиляция выполняется, но сообщения об ошибках из gcc не показываются в окне Output scite :
Код
scons: Reading SConscript files ...
scons: done reading SConscript files.
scons: Building targets ...
gcc -o out\test_01.o -c test_01.c
scons: *** [out\test_01.o] Error 1
scons: building terminated because of errors.
>Exit code: 2


а должно быть (при компиляции из ком.строки) :
Код
scons: Reading SConscript files ...
scons: done reading SConscript files.
scons: Building targets ...
gcc -o out\test_01.o -c test_01.c
test_01.c: In function 'main':
test_01.c:6: error: 's' undeclared (first use in this function)
test_01.c:6: error: (Each undeclared identifier is reported only once
test_01.c:6: error: for each function it appears in.)
test_01.c:6: error: expected ')' before string constant
scons: *** [out\test_01.o] Error 1
scons: building terminated because of errors.
dxp
Цитата(umup @ May 1 2008, 21:55) *
создал Sconscript :

...

1) как одним параметром указать, в какую папку должны помещаться выходные файлы (чтобы не замусоривать папку с исходниками - нужно скомпилировать в локальную папку out/) ?

2) как заставить scite показать вывод из gcc ?

добавил в cpp.properties :
command.build.*.c=scons.py
...

Я не стал заморачиваться с этими вещами. Написал свое. Запуск тулов выполняется через subprocess.Popen. Далее можно перехватывать вывод через PIPE и обрабатывать его, если надо (кое-где применяю), а можно так пускать - все выводит без потерь. Соответственно, папку вывода задаю в ключах компилятору, а не сконсу. Вот, для примера, action функция builder'а, которая компиляет срр файлы:

Код
#-------------------------------------------------------------------------------
#
#    Build object file from cpp source file
#
def compile_cpp(target, source, env):

    #------------------------------------------------
    #
    #   Launch compiler
    #
    print 'Compile:  ' + str(source[0])
    cmd = env['CC'] + env['CFLAGS'] + ' ' + str(source[0])
    p = subprocess.Popen(cmd, universal_newlines = True,
                         stdin  = subprocess.PIPE,
                         stdout = subprocess.PIPE,
                         stderr = subprocess.PIPE )

    out, err = p.communicate()
    out += err

    oerr = utils.handle_err(out) # перехват вывода и его обработка
    if oerr: print oerr

    rcode = p.returncode

    if rcode != 0:
        return rcode

    sfile_name = os.path.splitext(str(target[0]))[0] + '.s'
    vdsp_lst.create_lst(sfile_name)   # доп. действие - формирование файла листинга из асма (вставка строк из исходника по ссылкам - это нюанс vdsp)

#-------------------------------------------------------------------------------
Непомнящий Евгений
Цитата(umup @ May 1 2008, 18:55) *
1) как одним параметром указать, в какую папку должны помещаться выходные файлы (чтобы не замусоривать папку с исходниками - нужно скомпилировать в локальную папку out/) ?

у меня примерно так:
Код
files = """
    sources/pver.c
    sources/compDT.cpp
    sources/data.cpp            
    sources/defaults.cpp    
... """

buildDir = 'build/obj/'

for x in files.split('\n'):
  x = x.strip()  
  filename = os.path.splitext(x)[0]    
  env.Object(source = fullname, target = buildDir + filename + '.r90')


Цитата
2) как заставить scite показать вывод из gcc ?

Странно, у меня весь вывод показывается (правда, у меня IAR). А что у вас за версия scons?
umup
Цитата
А что у вас за версия scons

scons 0.98.2
scite 1.70 portable

еще scite не может запустить scons.py, приходится вызывать его из bat файла.
Непомнящий Евгений
Цитата(umup @ May 6 2008, 19:11) *
еще scite не может запустить scons.py, приходится вызывать его из bat файла.

вы под виндой сидите? Сконс создает батник scons.bat в python\scripts, где написан код для вызова скрипта и передачи ему аргументов. Если добавить этот путь к path, то в директории с sconstruct вызываете scons и понеслась...
AKimbo
Знатоки scons'а, помогите рабочим примером скрипта использующего tool отличный от идущих в комплекте. Интересует, собственно, где задаются пути к используемым компилятору/линкеру. Если можно, направьте в правильном направлении - хочу для сборки проекта использовать IAR'овские компилятор/линкер.
Непомнящий Евгений
Моя функция для создания environment под IAR
Код
from os.path import join
import os
import sys
import string
sys.path = [ join(sys.prefix, 'Lib', 'site-packages', 'scons-0.97.0d20071212')] + sys.path
from SCons.Environment import Environment

def EnvironmentIAR (iarDir, linkerDefs, numOfAddTargets = 0):
  env = Environment(ENV = os.environ)  
  PROC_DIR = iarDir + r'/avr'
  LINKER_DIR = iarDir + r'/common/bin'
  
  env['OBJSUFFIX'] = '.r90'
  env['PROGSUFFIX'] = '.hex'
  env['PROC_DIR'] = PROC_DIR
  env['CPPPATH'] = ['$PROC_DIR/INC', '$PROC_DIR/INC/$LIB']  
  env['CC_DIR'] = '"' + PROC_DIR + '"'
  env['CC'] = '"' + PROC_DIR + '/bin/iccavr.exe"'
  env['CXXCOM'] = '$CXX $SOURCES $CCCOMFLAGS $CXXFLAGS'
  env['CCCOM'] = env['CXXCOM']
  env['LIBOBJFILE'] = '$CC_DIR\LIB\$LIB\$($LIBFILE$).h'
  env['CXXFLAGS'] = r"--silent --cpu=$CPU -m$MEMORY_MODEL --no_wrap_diagnostics -y" + \
                  "  -e --debug --initializers_in_flash -$OPT --eeprom_size $EEPROM_SIZE -DENABLE_BIT_DEFINITIONS" + \
                  " $LANGUAGE --dlib_config $LIBOBJFILE -o $TARGET $OBJLIST $CXXADDFLAGS"
  env['CCCOMFLAGS'] = '$CPPFLAGS $_CPPDEFFLAGS $_CPPINCFLAGS'
  env['INCPREFIX'] = '-I '
  env['CCCOMSTR'] = 'Compiling $SOURCE -> $TARGET ...'
  env['CXXCOMSTR'] = env['CCCOMSTR']
  
  env['LINK'] = '"' + LINKER_DIR + '\\xlink.exe"'
  env['LINK_LIB'] = '"%s\\LIB\\$LIB\\$($LIBFILE$).r90"' % (PROC_DIR)
  
  targets = '-o $TARGET -F$OUT1_FORMAT '
  for i in xrange(numOfAddTargets):
      targets += '-O$OUT%d_FORMAT=$($TARGET$)$OUT%d_EXT' % (i+2, i+2)
  env['_TARGETS'] = targets
  
  env['LIST'] = '-l $($TARGET$).html -x$LIST_FORMAT'
  env['INCLUDE'] = ''

  segments = ''
  for s in string.split(linkerDefs):
      if s[0] == '@':
       segments += '-f "%s\\src\\template\\%s" ' % (PROC_DIR, s[1:])
      else:
       segments += s + ' '
  env['SEGMENTS'] = segments
  
  env['PROG_START'] = '-s __program_start'
  env['LINKCOM'] = '$LINK $SOURCES $LINK_LIB $_TARGETS $LIST $INCLUDE $SEGMENTS $PROG_START'
  env['LINKCOMSTR'] = "Linking $TARGET"
  
  return env


linkerDefs - это строка, примерно такая
linker_defs128 = '''
@cfgm128.xcl
-D_..X_HEAP_SIZE=0
-D_..X_TINY_HEAP_SIZE=0
-D_..X_NEAR_HEAP_SIZE=0
-D_..X_FAR_HEAP_SIZE=0
-D_..X_HUGE_HEAP_SIZE=0
-D_..X_CSTACK_SIZE=$CSTACK
-D_..X_RSTACK_SIZE=$RSTACK
@cfg3s.xcl
-D_..X_FLASH_BASE=_..X_INTVEC_SIZE
-H1895
-h(CODE)0-(_..X_INTVEC_SIZE-1)
-D_..X_EXT_SRAM_BASE=_..X_SRAM_END
-D_..X_EXT_SRAM_SIZE=0
-D_..X_EXT_ROM_BASE=_..X_SRAM_END
-D_..X_EXT_ROM_SIZE=0
-D_..X_EXT_NV_BASE=_..X_SRAM_END
-D_..X_EXT_NV_SIZE=0
-D_..X_CSTACK_BASE=_..X_SRAM_BASE
-D_..X_CSTACK_END=_..X_SRAM_END
-D_..X_RSTACK_BASE=_..X_SRAM_BASE
-D_..X_RSTACK_END=_..X_SRAM_END
'''
Вместо @ подставится путь к файлу

Юзать примерно так:
Код
env = EnvironmentIAR(os.environ['IAR'], ut.linker_defs128, 1)

# директивы компилятора
env['CPU'] = 'm128'
env['MEMORY_MODEL'] = 'small'
env['OPT'] = 's9'
env['EEPROM_SIZE'] = 4096
env['LANGUAGE'] = '--eec++'
env['OUT1_FORMAT'] = 'intel-extended'
env['OUT2_FORMAT'] = 'ubrof8'
env['OUT2_EXT'] = '.dbg'
env['LIST_FORMAT'] = 'msniohe'
env['CSTACK'] = 150
env['RSTACK'] = 'BE'
env['OBJLIST'] = "-lCN build\\list\\"
env['LIB'] = 'dlib'
env['LIBFILE'] = 'dlAVR-3s-ec_mul-n'
env['DEF_VAR'] = defVar
env['CXXADDFLAGS'] = '--preinclude sources/preinc103mk1.h'
dxp
Цитата(AKimbo @ May 13 2008, 18:50) *
Знатоки scons'а, помогите рабочим примером скрипта использующего tool отличный от идущих в комплекте. Интересует, собственно, где задаются пути к используемым компилятору/линкеру. Если можно, направьте в правильном направлении - хочу для сборки проекта использовать IAR'овские компилятор/линкер.

Все просто, там не столько сконсовское, сколько питоновое. Сначала можно задать тулзы и пути, например, так:

Код
#-------------------------------------------------------------------------------
#
#      Toolkit
#
IAR = os.environ['IAR']
TOOLKIT_PATH = IAR + '\\EW430v410'

ASM    = TOOLKIT_PATH + '\\430\\bin\\a430.exe'
CC     = TOOLKIT_PATH + '\\430\\bin\\icc430.exe'
Linker = TOOLKIT_PATH + '\\430\\bin\\xlink.exe'

ToolkitIncPath = [TOOLKIT_PATH + '\\430\\inc',  
                  TOOLKIT_PATH + '\\430\\inc\\dlib']

ToolkitLibPath = [TOOLKIT_PATH + '\\430\\lib\\dlib']
ToolkitCfgPath = [TOOLKIT_PATH + '\\430\\config']


Для чего через переменную окружения IAR, думаю, понятно - чтобы не привязываться к абсолютным путям на конкретной машине.

Затем задать тулзы в рабочем словаре env:

Код
env = Environment(TOOLS = {})

env['BUILDERS'] = { 'asmObj' : asm2obj, 'cppObj' : cpp2obj, 'Exe' : build_exe }
env['ASM'        ] = ASM
env['CC'         ] = CC
env['LINKER'     ] = Linker
env['AFLAGS'     ] = AFLAGS
env['CFLAGS'     ] = CFLAGS
env['LFLAGS'     ] = LFLAGS
env['CPPPATH'    ] = SourceDirs + ToolkitIncPath
env['FIRST_ENTRY'] = FirstEntry


Пример функции-билдера уже приводил. Полный скрипт во вложении. Это для EW430. Аналогичный есть для EWAVR и для Blackfin (VisualDSP++ 4.5).

Комментарий.
Скрипт строит список файлов с расширенями с, срр и ассемблера, находящихся в директориях, указанных в списке SourceDirs, и на основе этого списка производит сборку проекта. Т.е. если надо добавить файл в проект, достаточно положить его в одну из указанных директорий (если убрать из проекта - соответственно, удалить из директории либо изменить расширение). Поддерживаются мнимые цели clean и rebuild. Скрипт работает со структурой проекта (директории):

Config - скрипты линкера и подобное
Exe - исполняемые (hex и дебажный бинарник)
List - листинги и map файл линкера
Obj - объектные файлы

Если этих директорий не существует, скрипт при первом запуске создает их - чтобы тулзам было куда складывать продукты генерации. Получается аккуратно и удобно.

Успехов.
AKimbo
Спасибо всем, очень помогли. Теперь уход с IAR IDE будет менее болезненным. Если вы, DXP, не против - я позаимствую ваш скрипт, с минимальными изменениями. Понимать Питон понимаю, но вот самому написать пока слабо - ничего сложнее парсеров текста писать не приходилось. Но мощь и легкость применения еще как чувствуются.
AKimbo
Вопрос к вам, DXP.
Есть ли способ заставить функцию Builder'а запускающую линкер, выполнять пересборку при изменении не только списка sources, но и некоторого постороннего файла? Имеется в виду файл конфигурации Линкера *.icf. Можно , конечно, отслеживать это своей функцией запускающей скрипт с опцией rebuild, но как- то это не красиво.
Изменил ваш скрипт под свои нужды + IAR EWARM 5.0, если разрешите - могу выложить.
dxp
Цитата(AKimbo @ May 22 2008, 21:01) *
Есть ли способ заставить функцию Builder'а запускающую линкер, выполнять пересборку при изменении не только списка sources, но и некоторого постороннего файла? Имеется в виду файл конфигурации Линкера *.icf. Можно , конечно, отслеживать это своей функцией запускающей скрипт с опцией rebuild, но как- то это не красиво.

Вижу тут два варианта. Можно этот файл включить в список зависимостей, но тогда внутри функции билдера придется делать разбор списка и формировать отдельно список объектников и отфильтровывать его от конфигов. В принципе, это несложно, список все равно там формируется - в том же цикле проверять имя файла и пропускать файлы конфигов и все остальные, кто не объектные.

Второй вариант - сделать другой билдер, который будет зависеть от конфигов. Но ему придется передавать тогда как-то список объектников. Наверное, первый вариант проще.

Цитата(AKimbo @ May 22 2008, 21:01) *
Изменил ваш скрипт под свои нужды + IAR EWARM 5.0, если разрешите - могу выложить.

Это сколько угодно. smile.gif
AKimbo
Цитата(dxp @ May 23 2008, 07:56) *
...Можно этот файл включить в список зависимостей, но тогда внутри функции билдера придется делать разбор списка и формировать отдельно список объектников и отфильтровывать его от конфигов.

Так и сделал - конфиг. файл добавляю последним элементом в список sources и при разборе внутри action функции он отфильтровывается.

Итак, в приложении вариант сборщика на основе скрипта DXP. Основные моменты и принципы остались без изменения, адаптирован под IAR EWARM5.0.

Отличия:
Переваривает исходники *.c а не *.cpp
Другие ключики ассемблера/компилятора/линкера
Добавлена директория Config для конфиг. линкера *.icf, отслеживает его изменения при сборке.
Две набора ключей линкера - debug и release.
Создает два выходных файла формата ELF/DWARF - основной *.out и для отладки *.dbg
Конвертирует выходной *.out посредством утилитки Objcopy в *.hex и *.bin

Замечания:
Контрольную сумму в *.hex и *.bin не добавляет, не проблема если отладчик/загрузчик делает это сам.
Протестировано на проекте C+ASM, собирается и работает нормально.
dxp
Цитата(AKimbo @ May 23 2008, 20:57) *
...


Зависимости работают? Проверяли? Ну, в смысле, если меняете заголовочный файл, то система должна пересобрать все исходники, от которых он зависит. Спрашиваю потому, что не увидел определения

env['CPPPATH']

Этот элемент словаря задает путь для сканера заголовков. Если заголовочный файл находится в той же директории, что и исходный, то и без этого работает, но если заголовок в другой директории, нежели исходный, который включает заголовок, то без указанного элемента будут проблемы - сканер не найдет заголовка и не включит его в зависимость. Проверьте.

P.S.
По стилю. Названия функций в питон-сообществе принято писать строчными буквами (с разделениями подчеркиваниями), а с отбоем регистра прописными буквами - классы, объекты и т.д. Когда этот скрипт писАлся, я еще этого не знал, знакомые питонисты объяснили. smile.gif Теперь пишу "правильно". Хотя это мелочи, конечно. smile.gif
AKimbo
Цитата(dxp @ May 24 2008, 16:26) *
...

Зависимости между файлами, находящимися в разных директориях, действительно не работают. Волосы дыбом встали - такую ошибку пропустить, спасибо DXP что заметили. Лечится добавлением CPPPATH с путями ко всем директориям с изменяющимися *.h.
Про оформление Питона понял, но это процесс естественный - если много занимаешься то постепенно приходишь к правильным формам.
Товарищи, если кто будет пользоваться скриптом, добавьте:
Код
env['CPPPATH'] = SourceDirs + ToolkitIncPath + ToolkitLibPath
Fat Robot
Чтобы не плодить тем:

12 August 2008
SCons 1.0.0 is now available from the download page at SourceForge. This release is functionally the same as the 0.98.5 candidate, with documentation updates.

http://www.scons.org/

Успехов
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2014 Invision Power Services, Inc.