Самый простой способ изменить порядок строк в переменной make

Скажем, у вас есть переменная в фрагменте файла makefile, как показано ниже:

MY_LIST=a b c d

Как мне изменить порядок этого списка? Мне нужно:

$(warning MY_LIST=${MY_LIST}) 

чтобы показать

MY_LIST=d c b a

Изменить: реальная проблема заключается в том, что

ld -r some_object.o ${MY_LIST}

создает a.out с символами undefined, потому что элементы в MY_LIST являются фактически архивами, но в неправильном порядке. Если порядок MY_LIST отменяется, он будет правильно связываться (я думаю). Если вы знаете более разумный способ получить правильный порядок ссылок, подскажите мне.

Ответ 1

Решение в чистом GNU делает:

default: all

foo = пожалуйста, измените меня

reverse = $(если $(1), $(вызов reverse, $(wordlist 2, $(слова $(1)), $(1)))) $(первое слово $(1))

all: @echo $(call reverse, $(foo))

дает:

$make

меня обратный пожалуйста

Ответ 2

Вы также можете определить группы поиска с помощью ld:

ld -r foo.o -( a.a b.a c.a -)

Будет выполняться итерация через a.a, b.a и c.a до тех пор, пока никакие новые неразрешенные символы не будут удовлетворены любым объектом в группе.

Если вы используете gnu ld, вы также можете:

ld -r -o foo.o --whole-archive bar.a

Это немного сильнее, поскольку он будет включать в себя каждый объект из bar.a, независимо от того, удовлетворяет ли он неустановленному символу из foo.o.

Ответ 3

Улучшение решения GNU:

reverse = $(if $(wordlist 2,2, $(1)), $(вызов reverse, $(wordlist 2, $(слова $(1)), $(1))) $(firstword $(1)), $(1))

  • лучшее условие остановки, оригинал использует пустую строку, теряющую вызов функции
  • не добавляет ведущее пространство в обратный список, в отличие от оригинала

Ответ 4

Doh! Я мог бы просто использовать оболочку script -let:

(for d in ${MY_LIST}; do echo $$d; done) | tac

Ответ 5

Играя как с Ben Collins, так и с elmarco's, вот пунт к bash, который обрабатывает пробелы "правильно" 1

reverse = $(shell printf "%s\n" $(strip $1) | tac)

который делает правильную вещь, благодаря $(shell) автоматически очищая пробел и printf автоматически форматируя каждое слово в списке своих аргументов:

$(info [ $(call reverse,  one two   three four  ) ] )

дает:

[ four three two one ]

1... согласно моему ограниченному тестовому примеру (т.е. линии $(info ...), выше).