# SIMD and compiled code

**URL:** <https://discourse.julialang.org/t/simd-and-compiled-code/52082>\
**Category:** Performance\
**Tags:** simd\
**Created:** [December 19, 2020, 9:30am UTC](https://discourse.julialang.org/t/simd-and-compiled-code/52082 "2020-12-19T09:30:08Z")\
**Posts on this page:** 6\
**Page:** 1

<div class="post-metadata">

**Author:** ![lungben](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/lungben/32/12314_2.png) [@lungben](https://discourse.julialang.org/u/lungben)\
**Post date:** [December 19, 2020, 9:30am UTC](https://discourse.julialang.org/t/simd-and-compiled-code/52082/1 "2020-12-19T09:30:08Z")

</div>

Hi,

Different processors have different SIMD capabilities, especially different vector sizes on which the processor can work at once.  
However, there are a few points w.r.t. code compilation which I am not sure about.

If I understood correctly, Julia generates automatically SIMD code optimal to the current machine. It is able to do so because the code is compiled on the individual machine.  
Pre-compiled binaries for shipping, however, would either need to be compiled for the lowest common denominator (i.e. not using SIMD capabilities of most modern CPUs to full extend) or require explicit treatment of different SIMD capabilities at runtime, correct?

What about the default Julia sysimage? Would it increase runtime speed of (some) base functionality if the sysimage is recompiled on the individual machine, taking its full SIMD capabilities into accout?

---

<div class="post-metadata">

**Author:** ![carstenbauer](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/carstenbauer/32/4981_2.png) [@carstenbauer](https://discourse.julialang.org/u/carstenbauer)\
**Post date:** [December 19, 2020, 9:46am UTC](https://discourse.julialang.org/t/simd-and-compiled-code/52082/2 "2020-12-19T09:46:08Z")

</div>

I had a related question a few years back. There I asked whether it matters which compiler (`icc` vs `gcc`) one uses when building Julia. The answer was pretty much no.

> [@Building Julia: Does the compiler matter?](https://discourse.julialang.org/t/building-julia-does-the-compiler-matter/6858):
>
> I want to use Julia with MKL. As has been discussed, one currently has two options: use Julia Pro or build Julia from sources and setting flags. For many reasons I want to take the second approach. Regarding performance, what compiler should I use to build Julia, icc or gcc? Does the choice influence performance at all. [Here](https://discourse.julialang.org/t/building-julia-0-6-0-with-mkl-on-osx-10-12-5/5073/5) it has been mentioned that “Code generation is doen by LLVM so runtime performance AFAIU, run time performance should not depend on what you use to compile LLVM / Julia wit…

---

<div class="post-metadata">

**Author:** ![yuyichao](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yuyichao/32/20_2.png) [@yuyichao](https://discourse.julialang.org/u/yuyichao)\
**Post date:** [December 19, 2020, 10:55am UTC](https://discourse.julialang.org/t/simd-and-compiled-code/52082/3 "2020-12-19T10:55:54Z")

</div>

This question asked about the system image which is not related to the compiler used to compile julia itself. The default system image is simutaniously compiled for mulitple microarchs to take advantage of the different cpu features including SIMD.

---

<div class="post-metadata">

**Author:** ![carstenbauer](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/carstenbauer/32/4981_2.png) [@carstenbauer](https://discourse.julialang.org/u/carstenbauer)\
**Post date:** [December 19, 2020, 12:35pm UTC](https://discourse.julialang.org/t/simd-and-compiled-code/52082/4 "2020-12-19T12:35:13Z")

</div>

> [@yuyichao](#):
>
> The default system image is simutaniously compiled for mulitple microarchs to take advantage of the different cpu features including SIMD

If I compile Julia myself, is the resulting system image also compiled for multiple microarchs?

Update: I guess what I’m really asking is how independent the compilation of the system image is from and during the compilation of Julia itself. From [System Image Building · The Julia Language](https://docs.julialang.org/en/v1/devdocs/sysimg/) I take that this can be specified by a make option “during system image compilation”.

Update2: In [https://github.com/JuliaLang/julia/blob/master/Make.inc](https://github.com/JuliaLang/julia/blob/master/Make.inc) I found:

```julia
# JULIA_CPU_TARGET is the JIT-only complement to MARCH. Setting it explicitly is not generally necessary,
# since it is set equal to MARCH by default

```

Does this imply that the system image obtained when building Julia from source is not for multiple microarchs?

---

<div class="post-metadata">

**Author:** ![ffevotte](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ffevotte/32/6587_2.png) [@ffevotte](https://discourse.julialang.org/u/ffevotte)\
**Post date:** [December 19, 2020, 1:35pm UTC](https://discourse.julialang.org/t/simd-and-compiled-code/52082/5 "2020-12-19T13:35:07Z")

</div>

> [@lungben](#):
>
> Pre-compiled binaries for shipping, however, would either need to be compiled for the lowest common denominator (i.e. not using SIMD capabilities of most modern CPUs to full extend) or require explicit treatment of different SIMD capabilities at runtime, correct?

AFAIU Julia supports an intermediate technique between the two you mention: it can bake into one sysimage several versions of the same code, compiled and optimized for different micro architectures. So that it achieves the best of both worlds: (almost-)fully optimized code and no run-time latency (for what gets baked into the system image).

> [@lungben](#):
>
> What about the default Julia sysimage? Would it increase runtime speed of (some) base functionality if the sysimage is recompiled on the individual machine, taking its full SIMD capabilities into accout?

As explained in the [devdocs](https://docs.julialang.org/en/v1/devdocs/sysimg/#Specifying-multiple-system-image-targets), this is what’s used for the default sysimage that is shipped with official pre-built julia releases is compiled.

If you want to use [`PackageCompiler`](https://github.com/JuliaLang/PackageCompiler.jl) to produce custom system images for your own packages, you can achieve the same effect (i.e. produce sysimages that are both portable and optimized) using the `cpu_target` keyword argument to [`create_sysimage`](https://julialang.github.io/PackageCompiler.jl/dev/refs/#PackageCompiler.create_sysimage). For example for `x86_64` architectures:

```julia
create_sysimage(
    packages,
    sysimage_path = "my_sysimage.so",
    # [other kw args]
    cpu_target = "generic;sandybridge,-xsaveopt,clone_all;haswell,-rdrnd,base(1)"
)

```

---

<div class="post-metadata">

**Author:** ![lungben](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/lungben/32/12314_2.png) [@lungben](https://discourse.julialang.org/u/lungben)\
**Post date:** [December 19, 2020, 4:33pm UTC](https://discourse.julialang.org/t/simd-and-compiled-code/52082/6 "2020-12-19T16:33:14Z")

</div>

Thanks for your anwers @yuyichao and @ffevotte!  
I assume Fortran and C compiler are working in the same way, i.e. compiling binaries for different micro-architectures, correct?
