-
Notifications
You must be signed in to change notification settings - Fork 458
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
Better method for managing clang-format binaries #673
Comments
@akornilov feel free to ignore, but I see that you maintain the only llvm plugins in the gradle plugin portal. Any tips? |
Hello,
Can you please explain in details what kind of tips you expect from me?
|
When a user declares We'd like to do something similar for Do you have any suggestions for how to grab and cache llvm binaries, or better yet just the clang-format part of the binaries? Thanks, and "not interested" is a fine answer, don't mean to bother 😁 |
Hi Ned,
Are you from the Gradle developers team?
What kind of software do you develop at the moment (I mean software which is related with this topic)?
Is it Gradle core or some plugin to have support for LLVM with Gradle?
Looks like you need something like my already created plugin for Gradle which allows you to use LLVM libraries (shared or static linkage) in a simple way :)
Do you know anything about my plugin?
Please take a look here: https://sourceforge.net/p/gradle-cpp/wiki/cpp-llvm
Integration with LLVM is very simple:
plugins {
id 'cpp-application'
id 'loggersoft.cpp-llvm' version '1.9'
}
llvm {
version = '10.0.0'
linkage = Linkage.SHARED
suppressWarningsMsvc = true
}
For the shared linkage version of LLVM library I use default Gradle format for C++ artifacts (some kind of Maven) cpp-library + maven-publish plugins. There you can find binaries which my plugin uses (LLVM 9 and 10 yet).
https://sourceforge.net/projects/llvm-binaries/files/maven/org/llvm
For static linkage version of LLVM I use prebuild archives with LLVM binaries from official LLVM site (e.g. https://releases.llvm.org/8.0.0/clang+llvm-8.0.0-x86_64-linux-gnu-ubuntu-18.04.tar.xz) or unofficial builds prepared by myself and hosted on Source Forge: https://sourceforge.net/projects/llvm-binaries/files.
During build my Gradle plugin downloads archive (if it didn't download before) with the required version and puts it in the Gradle folder in the current user home directory. After that extracts archive and add to compiler and linker all necessary options include paths to headers and libraries. Also plugin supports the list of particular LLVM components to choose only
exactly required for a project, because LLVM has too many separate libraries for static linkage (about ~150 static libraries).
The source of cpp-llvm plugin you can found here: cpp-llvm <https://sourceforge.net/p/gradle-cpp/code/ci/default/tree/plugins/cpp-llvm>
Feel free to ask my if something is not clear or I didn't answer on you original question :)
|
Thanks, this is very helpful!!
I'm not affiliated with Gradle. I work on tooling for embedded systems, and Spotless is a side project that does autoformatting. I don't use llvm to compile, but I do want to use
Perfect, this is exactly what I was looking for, thanks very much! I found your plugin at https://plugins.gradle.org/, but I couldn't figure out if it did installation for you, or if the user still needed to do that themselves. I think where I got stuck is that I didn't think to click the "wiki" section, where you have very good documentation. What I like about GitHub is that the README shows up really big, so it's easy to tell new users the details of the project. The SourceForge landing page doesn't leave much space for documentation, so it can be hard to figure out where to get started. But now I know where to start! |
Hi, I recently started using Spotless (awesome project!), and found it very frustrating to use with If I understand correctly, the purpose of the strict version check is to allow safe caching. Then, why not instead of enforcing a specific version, just invalidating/ignoring the cache in case of a version mismatch? IMO this would make Moreover, if the purpose of the strict version check is also to control the allowed version of |
That's one aspect, but the other part is to make sure that the team and CI are all on the same page. You've got But it's definitely a problem if we are including a platform-specific identifier, that ought to get stripped off the check. The way to do that is to add
I might have the regex there wrong, the default is this:
We need to add a non-capturing group to grab the hyphen in the platform-specific part and keep it out of the version group. |
Would it be possible to only fail the build if a clang-format call actually happens? The gradle plugin crashes the build during the configuration phase if it is not available or the wrong version, no matter which tasks are run. Context: I have some CI scanning jobs on my projects and I cannot easily change the images used. I would love to use the spotless plugin but if I have to choose between vulnerability scanning and a nice format I will take vulnerability scanning. |
I'm afraid that this is not good enough, because the minor/patch parts of the version might also differ across distros. I think that Spotless should either assert only the major version part, or it should allow the user to customize the version check by supplying a custom regex pattern. |
Yes, this is possible, but a bit tricky. You can see here that
This could instead be a spotless/lib/src/main/java/com/diffplug/spotless/cpp/ClangFormatStep.java Lines 94 to 104 in 8797048
I think your feature request for this is a good one, and it's probably worth somehow generalizing this lazy construction of args into the
I'm happy to merge a PR which supports this too, the tricky part is docs. When you first encountered this issue of different clang-format-9's, and you looked at our docs, what do you wish it had said? Figure that out, and then building to it would be easy. |
Thanks to @bh-tt, starting with Still happy to merge a PR to allow new version regex. One thought which just occurred to me - you could make your build configuration platform-specific, e.g.: clang().version(if (ubuntu20) "9.0.1-12" else if (ubuntu18) "9.0.0-2~ubuntu18.04.2") Not great, but a possible workaround until something better comes along... |
I find the comment "version is optional" right after For those who want to detect the clang-format version, here's a snippet for build.gradle: def clangFormatBinary = (String) project.findProperty('clangFormat') ?: 'clang-format'
spotless {
java {
def clangOutput = new ByteArrayOutputStream()
exec {
commandLine clangFormatBinary, '--version'
standardOutput = clangOutput
}
def clangVersion = (String) (clangOutput.toString() =~ /\d+\.\d+\.\d+/)[0]
clangFormat(clangVersion).pathToExe(clangFormatBinary).style('file')
}
} Run with |
@nedtwigg what is the recommended way of handling clang-format for both macOS and Linux? The clang-format binary has a major version number appended at the end on Ubuntu (clang-format-15), but it can also just be called clang-format. Different LTS releases of Ubuntu has different versions of clang-format available as packages, so there isn't an obvious smallest common denominator that can be used. The snippet in my previous comment does what I want ("I tell Gradle the clang-format binary to use, Gradle figures out what version it is and how to use it without bothering me"), except that the snippet causes failures for people without clang-format installed on their computer. I understand people cannot format the code without clang-format, but |
You could set a |
We are able to call
clang-format
by shelling out to it on the system path, and we are able to cache its results by enforcing a version check on the binary. However, if it isn't on the path, or the version is wrong, we just show a helpful error message and let the user figure it out from there:spotless/lib/src/main/java/com/diffplug/spotless/cpp/ClangFormatStep.java
Lines 70 to 83 in 608e128
It would be nice if we could handle this better, or at least have better instructions.
The text was updated successfully, but these errors were encountered: