-
-
Notifications
You must be signed in to change notification settings - Fork 399
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
Add support of GFortran in MKL package #5258
base: dev
Are you sure you want to change the base?
Conversation
This patch introduces 3 modifications to the package MKL: - added support of Fortran and GFortran to compile with the MKL libraries - changed download paths following some changes made on the Intel channel of conda (see https://community.intel.com/t5/Intel-Integrated-Performance/Problems-installing-with-conda-HTTP-403-FORBIDDEN/m-p/1631577 for details). - added support of latest version of MKL as of September 2024: 2024.2.1 Note that the support of Intel processors on OS X seems to have been dropped by Intel. No path could be found. Content of the repository can be parsed from the JSON files in each architecture-dependent path: https://software.repos.intel.com/python/conda/<arch>/repodata.json with <arch> being one of the following: - "linux-32" - "linux-64" - "win-32" - "win-64" Minimum example with GFortran: Fortran code ``` program test_mkl use iso_fortran_env, only: real64 integer, parameter :: N = 10 integer :: info integer, dimension(N) :: iwork real(real64), dimension(N,N) :: A, B, C call random_number(A) call random_number(B) call dgemm('T','N',N,N,N,1.0_real64,A,N,B,N,0.0_real64,C,N) call dgetrf(N,N,C,N,iwork,info) end program test_mkl ``` xmake.lua ``` add_rules("mode.debug", "mode.release") add_repositories("local-repo xmake-repo") add_requires("mkl", { configs = { threading = "gomp" } }) target("test_mkl") set_kind("binary") set_policy("check.auto_ignore_flags", false) add_packages("mkl") add_files("test_mkl.f90") add_tests("default") ```
The repository was also available in the new repository. Versions listed in the package and not available in the repository have been removed or replaced with more recent ones from the same year.
Thank you very much. I have updated the package, restoring support of Intel Mac OS X and correcting the version. |
Fixed URLs to some Windows 32 packages and Linux (32 and 64 bits) packages.
packages/m/mkl/xmake.lua
Outdated
@@ -109,7 +113,8 @@ package("mkl") | |||
package:add("links", package:is_arch("x64", "x86_64") and "mkl_blas95_" .. suffix or "mkl_blas95") | |||
package:add("links", package:is_arch("x64", "x86_64") and "mkl_lapack95_" .. suffix or "mkl_lapack95") | |||
|
|||
if package:has_tool("cc", "gcc", "gxx") then | |||
if (package:has_tool("cc", "gcc", "gxx") or | |||
package:has_tool("fc", "gfortran")) then |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here we should check package:has_tool("cc", "cl", "clang-cl")
first, otherwise on windows if there is gfortran installed it will lead to incorrect link flags
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Basically it should also detect Apple clang since Apple clang do not support link groups. But I don't know how to tell Apple clang from llvm clang using package:has_tool() api. @waruqi any idea?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
use package:has_flags() instead of has_tool?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is there any other package I could use as reference for the correct test structure? The original versions of fetch.lua
and xmake.lua
had only this test.
Couldn't we use instead a test on toolkind
and the type of linker, as done for instance in the OpenMP package (ref:
xmake-repo/packages/o/openmp/xmake.lua
Line 60 in 9286276
for _, toolkind in ipairs({"ld", "fcld"}) do |
fcldflags
(see #5255)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
you can try, test linker will be better.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK. Should I use for now ldflags
for the fortran part?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fcldflags (binary) fcshflags (shared)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
xmake-repo/packages/o/openmp/xmake.lua
Lines 76 to 78 in f008565
elseif package:has_tool(toolkind, "gfortran") then | |
result.fcldflags = "-fopenmp" | |
result.fcshflags = "-fopenmp" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It seems the new test has improved the results of the tests (in the meantime I discovered I did not need to load add_configs for fetch.lua
for the 'runtime' test to work), but it still fails on Mac OS X x86-64.
Is it possible that the LLVM linker on Apple is also recognized as GCC?
Should I replace the test:
if (package:has_tool(toolkind, "gcc", "gxx") or package:has_tool(toolkind, "gfortran")) then
with something of the form:
if (not package:has_tool(toolkind, "clang", "clangxx") and (package:has_tool(toolkind, "gcc", "gxx") or package:has_tool(toolkind, "gfortran"))) then
?
For Fortran, I had to replace fcldflags
with ldflags
since the support of the former seems broken up to xmake xmake v2.9.5+dev.b938556. Using ldflags
is necessary to compile Fortran programs with GFortran on Linux AMD64. I have commented out the fcldflags
and fcshflags
for testing purposes in the package source.
The intel repository in pip is still alive https://pypi.org/project/mkl/#files https://pypi.org/project/mkl-static/#files https://pypi.org/project/mkl-devel/#files https://pypi.org/project/mkl-include/#files (However the format is ".whl" thus needs to unzip a sub-directory(filename.whl/$version.data/) inside it) |
The tests to set the linker flags are now based on "ld/fcld" instead of the compilers "cc/fc" to avoid problems with toolchains combining different tools.
Thank you very much for the information. I am not familiar enough with the internal tools of |
packages/m/mkl/fetch.lua
Outdated
@@ -1,6 +1,8 @@ | |||
import("lib.detect.find_path") | |||
import("lib.detect.find_library") | |||
|
|||
-- add_configs("runtime", {description = "Set MKL runtime for gcc/clang like compilers.", default = "default", type = "string", values = {"default", "custom"}}) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
remove unused comments
packages/m/mkl/fetch.lua
Outdated
else | ||
table.join2(result.links, group) | ||
for _, toolkind in ipairs({"ld", "fcld"}) do | ||
-- if package:config("runtime") == "default" then |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
remove comment
packages/m/mkl/fetch.lua
Outdated
table.join2(result.links, group) | ||
for _, toolkind in ipairs({"ld", "fcld"}) do | ||
-- if package:config("runtime") == "default" then | ||
if (package:has_tool(toolkind, "gcc", "gxx") or package:has_tool(toolkind, "gfortran")) then |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
remove ()
in if () then
packages/m/mkl/fetch.lua
Outdated
result.shflags = table.concat(flags, " ") | ||
else | ||
-- result.fcldflags = table.concat(flags, " ") | ||
-- result.fcshflags = table.concat(flags, " ") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
remove comment
packages/m/mkl/xmake.lua
Outdated
@@ -3,90 +3,96 @@ package("mkl") | |||
set_homepage("https://software.intel.com/content/www/us/en/develop/tools/oneapi/components/onemkl.html") | |||
set_description("Intel® oneAPI Math Kernel Library") | |||
|
|||
add_configs("runtime", {description = "Set MKL runtime for gcc/clang like compilers.", default = "default", type = "string", values = {"default", "custom"}}) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
runtime is builtin configuration, please rename to mkl_runtime
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sorry, I had not understood this command in the OpenMP package. At this point, there is no real need for this setup in MKL in my opinion, especially considering how complicated the configuration of the linker is. This should be set through the other parameters, so I have removed the reference.
packages/m/mkl/xmake.lua
Outdated
package:add("links", "mkl_gnu_thread", "gomp") | ||
for _, toolkind in ipairs({"ld", "fcld"}) do | ||
if package:config("runtime") == "default" then | ||
if (package:has_tool(toolkind, "gcc", "gxx") or package:has_tool(toolkind, "gfortran")) then |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
remove ()
packages/m/mkl/xmake.lua
Outdated
var_ldflags = 'ldflags' | ||
var_shflags = 'shflags' | ||
-- var_ldflags = 'fcldflags' | ||
-- var_shflags = 'fcshflags' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
remove comment
packages/m/mkl/xmake.lua
Outdated
if package:config("runtime") == "default" then | ||
if (package:has_tool(toolkind, "gcc", "gxx") or package:has_tool(toolkind, "gfortran")) then | ||
if package:has_tool(toolkind, "gcc", "gxx") then | ||
var_ldflags = 'ldflags' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
use ""
instead of ''
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
and please define it as local variable.
local var_ldflags
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I should have applied all the corrections. I had to change slightly the layout of the code to have the variables available in the parent block.
* Use of "" instead of '' for strings. * Removal of unnecessary parentheses. * Use of "local" for local variables. * Removed unnecessary comments.
Previous patches incorrectly referred to the runtime configuration, which is supposed to be built in and not set in package.
packages/m/mkl/fetch.lua
Outdated
for _, lib in ipairs(group) do | ||
result.ldflags = result.ldflags .. "-l" .. lib .. " " | ||
for _, toolkind in ipairs({"ld", "fcld"}) do | ||
if package:has_tool(toolkind, "gcc", "gxx") or package:has_tool(toolkind, "gfortran") then |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
package:has_tool(toolkind, "gcc", "gxx", "gfortran")
else | ||
result.ldflags = table.concat(flags, " ") | ||
result.shflags = table.concat(flags, " ") | ||
end |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
please simplify repeat table.concat, we need not call table.concat
if package:has_tool(toolkind, "gfortran") then
result.fcldflags = flags
result.fcshflags = flags
else
result.ldflags = flags
result.shflags = flags
end
packages/m/mkl/fetch.lua
Outdated
result.ldflags = table.concat(flags, " ") | ||
result.shflags = table.concat(flags, " ") | ||
else | ||
result.ldflags = table.concat(flags, " ") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fcldflags?
packages/m/mkl/xmake.lua
Outdated
elseif threading == "gomp" then | ||
package:add("links", "mkl_gnu_thread", "gomp") | ||
for _, toolkind in ipairs({"ld", "fcld"}) do | ||
if package:has_tool(toolkind, "gcc", "gxx") or package:has_tool(toolkind, "gfortran") then |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
and here
packages/m/mkl/xmake.lua
Outdated
local var_shflags = "shflags" | ||
if package:has_tool(toolkind, "gfortran") then | ||
var_ldflags = "ldflags" | ||
var_shflags = "shflags" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fcldflags, fcshflags?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The problem is that the package fails with toolchain=gfortran
because the linker flags are not properly set. This gives an error for both OpenMP (#5255) and MKL packages. If a special setting is necessary to get this to work with GFortran, could you send it to me, please?
We use xmake --toolchain=gfortran
. A minimum example is provided in the bug report #5255 .
The most recent tests were done with xmake v2.9.5+dev.9563841
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll take a look at this issue, but need to wait a few days as I've been busy in these days.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No problem, I am currently including the other changes you asked and will make the final changes as necessary, thank you very much!
Regarding the failure with Mac Intel x86_64, is there a workaround to make it work? Should we explicitly exclude clang with a condition like:
if not package:has_tool(toolkind, "clang", "clangxx") and package:has_tool(toolkind, "gcc", "gxx", "gfortran") then
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have supported fcldflags, you can try #5255 (comment)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have pushed the latest changes to the package with the edits you asked. This version works fine for gcc/clang toolchains but fails with gfortran (Linux Debian testing, latest version of xmake from the dev branch).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
but it works on ci.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is there any fortran/gfortran test in the test suite? From what I could see, only clang and gcc are tested, so the logic for gfortran is never controlled.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The fortran code test is not currently supported. Can you provide a test example project, I will try it.
packages/m/mkl/xmake.lua
Outdated
end | ||
table.insert(flags, "-lmkl_core") | ||
table.insert(flags, "-Wl,--end-group") | ||
package:add(var_ldflags, table.concat(flags, " ")) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
we need not call table.concat
The variables for the linker with GFortran are now set to fcldflags and fcshflags following the latest changes in xmake. Some redundant or awkward constructs were also fixed.
please wait for this patch xmake-io/xmake#5649 then you can add on_test(function (package)
import("lib.detect.find_tool")
if package.check_fcsnippets and find_tool("gfortran") then
assert(package:check_fcsnippets({test = [[
program hello
print *, "Hello World!"
end program hello
]]}))
end
end) to test fortan code and links. |
Added Fortran test if gfortran available.
any idea? |
I am investigating. I have already found one problem:
It seems that the test on the fcsnippet gives a false positive. I myself found that the test could fail because it looks for gfortran but will use whatever is the default for the Fortran compiler, in my case nvfortran. |
The test on the presence of gfortran may not guarantee the linker is properly set. The new test check that fcld is also set, for now to gfortran since the test on the Fortran compiler only considers this compiler. Note: this way, fcsnippets are only run if --toolchain=gfortran is set.
For now, I was able to identify a few issues with the current setup:
|
This may be caused by the use of precompiled mkl binary libraries. Binary libraries under Linux may have compatibility issues. and it works on my linux machine. |
on macOS
maybe we need add |
It seems that all are compatibility issues caused by mkl binary libraries. |
if I use g++ as linker, some fortran libs will be missing. > /usr/bin/g++ -o /tmp/.xmake999/240926/_CA59D77C6B80423084BB868ED6D8C940.b /tmp/.xmake999/240926/_CA59D77C6B80423084BB868ED6D8C940.o -m64 -Wl,--start-group -lmkl_intel_lp64 -lmkl_tbb_thread -lmkl_core -Wl,--end-group -L/home/ruki/.xmake/packages/m/mkl/2024.2.2+15/52a38912be4e4ed1bdfef80bb11ed833/lib -L/home/ruki/.xmake/packages/t/tbb/2021.12.0/df9ece8dadfc4b68be28a7546372f41e/lib -lmkl_blas95_lp64 -lmkl_lapack95_lp64 -ltbb -ltbbmalloc -ltbbmalloc_proxy -lpthread -ldl
/usr/bin/ld: /tmp/.xmake999/240926/_CA59D77C6B80423084BB868ED6D8C940.o: in function `main':
_FBF1AB2116944858B1A7CAC521022F86.f90:(.text+0xa2): undefined reference to `_gfortran_set_args'
/usr/bin/ld: _FBF1AB2116944858B1A7CAC521022F86.f90:(.text+0xb6): undefined reference to `_gfortran_set_options'
collect2: error: ld returned 1 exit status |
I tried to do this but failed. How should I add them in the snippets? |
It should be possible to fix these errors with |
It seems that the Fortran tests (fcsnippets) use the linker defined as |
I'm going to split this issue into 2 parts since the fortran things are still not fully solved, and fixing the broken urls is more important. See #5602 |
Add support for Fortran/GFortran with MKL
This patch addresses #5254 and introduces 3 modifications to the package MKL:
Note that the support of Intel processors on OS X seems to have been dropped by Intel. No path could be found.
Content of the repository can be parsed from the JSON files in each architecture-dependent path:
https://software.repos.intel.com/python/conda//repodata.json
with being one of the following:
Minimum example with GFortran:
Fortran code
xmake.lua