Как вы можете сделать ifdef guard для m4 макрофайла? - PullRequest
2 голосов
/ 18 марта 2011

Для заголовочных файлов C вы можете предотвратить многократное включение заголовочного файла, например:

#ifndef MY_FOO_H
#define MY_FOO_H

[...]

#endif

Как я могу сделать то же самое в m4, чтобы множественные вызовы макросов include() для одного и того же файлатолько чтобы содержимое было включено один раз?

В частности, я хочу сделать защиту ifdef, включающую использование макроса changequote (я не буду загромождать свой код dnl):

Первоначально, когда я делаю следующее, несколько включений по-прежнему портят кавычки:

changequote_file.m4:

ifdef(my_foo_m4,,define(my_foo_m4,1)
changequote([,])
)

changequote_invocation.m4:

include(changequote_file.m4)
After first include invocation:
[I should not have brackets around me]
`I should have normal m4 quotes around me'
include(changequote_file.m4)
After second include invocation:
[I should not have brackets around me]
`I should have normal m4 quotes around me'

Вызывается с m4 changequote_invocation.m4 выходами:

After first include invocation:
I should not have brackets around me
`I should have normal m4 quotes around me'


After second include invocation:
[I should not have brackets around me]
`I should have normal m4 quotes around me'

Ответы [ 2 ]

5 голосов
/ 18 марта 2011

Самый простой способ - это почти буквальный перевод cpp версии:

ifdef(`my_foo_m4',,`define(`my_foo_m4',1)dnl
(rest of file here)
')dnl

Таким образом, если определено my_foo_m4, файл расширяется до нуля, в противном случае его содержимое оценивается.

1 голос
/ 10 октября 2013

Я думаю, что на самом деле у вас есть 2 вопроса: - Как это сделать - почему это не работает в моем случае.

Способ сделать это почти так же, как вы, новам нужно все процитировать

ifdef(`my_foo_m4',,`define(`my_foo_m4',1)
  changequote([,])
')

Проблема заключается во втором включении файла, предложение было изменено, поэтому теоретически вы должны включить следующий файл (вы изменили предложение на [, ] поэтому все файлы, которые вы включаете, должны использовать [, ], не так ли?):

ifdef([my_foo_m4],,[define([my_foo_m4],1)
  changequote([[],])
])

но вы включаете тот же файл с оригинальной цитатой, поэтому выifdef находится на символе `my_foo_m4' (который, вероятно, недействителен), а не my_foo_m4, а бит else

define(`my_foo_m4',1)
  changequote([,])

не заключен в кавычки (не между []) и поэтому оценивается независимо от результата тестаэто означает, что он вызывает changequote с ,, то есть он вызывает

changequote(,)

, что отключает кавычку.

...