Skip to content

namespaced defines: -d:myproj.mykey to avoid clashes #181

@timotheecour

Description

@timotheecour

defines have global scope and can cause clashes.
nim itself defines 363 unique defines, many of which are not prefixed by nim, see the list here: https://gist.github.com/timotheecour/8b2286478083a6068731a63114ee9dd0

The current scheme (which is rarely followed) is to prefix by nimble package name, eg: -d:nimHasLibFFI
However this scheme is brittle because of style and case insensitivity of defines, so you can still have clashes, eg:
-d:fooBarBaz # could be interpreted as (package foo, var barBaz) or (package fooBar, var baz) or any other variation

This is a problem because many nimble packages are prefixes of each other, eg see https://gist.github.com/timotheecour/182fce669ff217c6b0bc87d918303c3e which shows 233 (package1, package2) pairs such that package1 is a prefix of package2.
Furthermore, plenty of packages start with nim so that further causes chances of define clashes.

There is a simple solution to that:

proposal

allow using a namespace for defines, eg:

nim c -d:myproj.mykey1 main.nim
nim c -d:myproj.mykey2:foo main.nim

# main.nim
when defined(myproj.mykey1): discard
const bar {.strdefine:"myproj.mykey2".} = "foo2"

we can just restrict (for simplicity) to at most a single dot, so that foo.bar is valid but not foo.bar.baz

this allows a nimble package foo to prefix all its defines by foo., eg -d:foo.bar

implementation difficulty

easy, I can do it if this RFC is accepted

note

see also #269 for a proposal that enforces ODR (one definition rule), that is complimentary to this RFC.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions