Acabei de pensar em uma ótima solução para isso, que funciona com os arquivos de origem e de cabeçalho, é muito eficiente e funciona em tempo de compilação em todas as plataformas sem extensões específicas do compilador. Essa solução também preserva a estrutura de diretórios relativa do seu projeto, para que você saiba em qual pasta o arquivo está e apenas em relação à raiz do seu projeto.
A idéia é obter o tamanho do diretório de origem com sua ferramenta de construção e apenas adicioná-lo à __FILE__
macro, removendo o diretório completamente e mostrando apenas o nome do arquivo começando no diretório de origem.
O exemplo a seguir é implementado usando o CMake, mas não há razão para que ele não funcione com outras ferramentas de construção, porque o truque é muito simples.
No arquivo CMakeLists.txt, defina uma macro que tenha o comprimento do caminho para o seu projeto no CMake:
# The additional / is important to remove the last character from the path.
# Note that it does not matter if the OS uses / or \, because we are only
# saving the path size.
string(LENGTH "${CMAKE_SOURCE_DIR}/" SOURCE_PATH_SIZE)
add_definitions("-DSOURCE_PATH_SIZE=${SOURCE_PATH_SIZE}")
No seu código-fonte, defina uma __FILENAME__
macro que apenas adicione o tamanho do caminho de origem à __FILE__
macro:
#define __FILENAME__ (__FILE__ + SOURCE_PATH_SIZE)
Em seguida, basta usar essa nova macro em vez da __FILE__
macro. Isso funciona porque o __FILE__
caminho sempre começa com o caminho para o diretório de origem do CMake. Ao removê-lo da __FILE__
string, o pré-processador se encarregará de especificar o nome correto do arquivo e tudo será relativo à raiz do seu projeto CMake.
Se você se preocupa com o desempenho, este é tão eficiente quanto usar __FILE__
, porque ambos __FILE__
e SOURCE_PATH_SIZE
são conhecidos constantes de tempo de compilação, para que possa ser otimizado afastado pelo compilador.
O único lugar em que isso falharia é se você estiver usando isso em arquivos gerados e eles estiverem em uma pasta de compilação externa. Então você provavelmente terá que criar outra macro usando a CMAKE_BUILD_DIR
variável em vez de CMAKE_SOURCE_DIR
.