Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Optimization for speed by code duplication #124

Open
cardillan opened this issue Feb 10, 2024 · 1 comment
Open

Optimization for speed by code duplication #124

cardillan opened this issue Feb 10, 2024 · 1 comment
Labels
enhancement New feature or request optimizer Related to the code optimizer

Comments

@cardillan
Copy link
Owner

Suggested by @limonovthesecond2 here.

In loops with expressions such as if-else and case after the expression is completed, the jump forwards to the next command after the comparing. However, we can inject all the code there instead.
Example:

i = 0
do
    block = getlink(i)
    case block
        when @unloader then print("unloader")
        when @sorter then print("sorter")
        else print("else")
    end
    i += 1
loop while i < @links

Compiles:

set i 0
getlink block i
jump 5 notEqual block @unloader
print "unloader"
jump 9 always 0 0
jump 8 notEqual block @sorter
print "sorter"
jump 9 always 0 0
print "else"
op add i i 1
jump 1 lessThan i @links
end

This code compiles with 2 jump 9 always, which redirects to the loop condition and adding a counter. Instead of this redirection, we can add code itself at the end of each condition, which will result in larger size but also greater efficiency. To avoid reaching the size limit, something like auto-function-inline can be used with a maximum operation size limit.

i = 0
while true
    block = getlink(i)
    case block
        when @unloader then
            print("unloader")
            i += 1
            if i >= @links
                end()
            end
        when @sorter then
            print("sorter")
            i += 1
            if i >= @links
                end()
            end
        else
            print("else")
            i += 1
            if i >= @links
                end()
            end
    end
end

Compiles:

set i 0
getlink block i
jump 7 notEqual block @unloader
print "unloader"
op add i i 1
jump 1 lessThan i @links
end
jump 12 notEqual block @sorter
print "sorter"
op add i i 1
jump 1 lessThan i @links
end
print "else"
op add i i 1
jump 1 lessThan i @links
end
end
@cardillan cardillan added the optimizer Related to the code optimizer label Feb 10, 2024
@cardillan
Copy link
Owner Author

cardillan commented Feb 11, 2024

It looks like this optimization could improve nested conditional expressions as well as loops:

if A
    if B print("B") else print("not B") end
    print("A")
else
    print("not A")
end

compiles to

jump 7 equal A false
jump 4 equal B false
print "B"
jump 5 always 0 0
print "not B"
print "A"
jump 0 always 0 0
print "not A"
end

which could be improved to

jump 8 equal A false
jump 5 equal B false
print "B"
print "A"
jump 0 always 0 0
print "not B"
print "A"
jump 0 always 0 0
print "not A"
end

An optimizer might therefore inspect every unconditional jump, and if it leads to a section of linear code ended by an unconditional jump, replace the jump with the target section of code. If the jump at the end of the section is conditional, and is part of a loop condition, the loop condition would be duplicated there.

In the initial implementation, complex structures (e.g. function calls or conditional expressions) wouldn't be copied.

Code optimizers (particularly the Data Flow Optimizer, but some others too) rely on the compiled code having certain expected structure. The DFO will need to be updated to understand the new structure.

@cardillan cardillan added the enhancement New feature or request label Dec 7, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request optimizer Related to the code optimizer
Projects
None yet
Development

No branches or pull requests

1 participant