Skip to content

Guide for @inbounds and @boundscheck #113

@Nagefire

Description

@Nagefire

Performance-critical Julia code usually performs bounds checks and input validation once before running (presumably) safe code. Macros such as @simd, @inbounds, and @turbo have been added to Julia to boost performance for safe code. However, the way that @inbounds propogation works allows for differing syntax with for loops:

@inbounds for i in 1:20
    x[i] = rand(1:i)
end

and

for i in 1:20
    @inbounds x[i] = rand(1:i)
end

have the same llvm representation. Another subtlety of propogation is that @inboundsdisables bound checks for entire lines;

@inbounds x[i] + y[j]

disables bounds check for both x and y, although the author of the code may have intended for the macro to only affect x. Another issue with propogation is that the syntax

@inbounds @simd for i in 1:20
    x[i] += rand(1:i)
end

does not actually disable bounds checks for x (as specified in the docs of @simd).

To avoid confusion and ambiguity with the use of @inbounds (and other macros), I propose that we add a section on macro calls, specifying that the code meant to be modified by the macro should be enclosed in parentheses. Examples of proper usage

for i in 1:20
    x[i] += @inbounds(x[end-i])
end
@inbounds(x[i] += sum(y[A]))

Examples of improper usage

@inbounds x[3]
@inbounds for i in 1:20
    print(x[i])
end

Assignments are special in the case of @inbounds, as the macro can affect both the left- and right-hand sides or only the right-hand side. The only method of dropping bounds check for only the right-hand side is via the syntax

=(@inbounds(x[3]), x[4])

which should be avoided completely.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions