1 /*
2  * Copyright 2023 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package androidx.build.clang
18 
19 import javax.inject.Inject
20 import org.gradle.api.DefaultTask
21 import org.gradle.api.file.ConfigurableFileCollection
22 import org.gradle.api.file.DirectoryProperty
23 import org.gradle.api.provider.ListProperty
24 import org.gradle.api.provider.Property
25 import org.gradle.api.services.ServiceReference
26 import org.gradle.api.tasks.CacheableTask
27 import org.gradle.api.tasks.Input
28 import org.gradle.api.tasks.InputFiles
29 import org.gradle.api.tasks.Nested
30 import org.gradle.api.tasks.OutputDirectory
31 import org.gradle.api.tasks.PathSensitive
32 import org.gradle.api.tasks.PathSensitivity
33 import org.gradle.api.tasks.TaskAction
34 import org.gradle.workers.WorkAction
35 import org.gradle.workers.WorkParameters
36 import org.gradle.workers.WorkerExecutor
37 
38 @CacheableTask
39 abstract class ClangCompileTask @Inject constructor(private val workerExecutor: WorkerExecutor) :
40     DefaultTask() {
41     init {
42         description = "Compiles C sources into an object file (.o)."
43         group = "Build"
44     }
45 
46     @get:ServiceReference(KonanBuildService.KEY)
47     abstract val konanBuildService: Property<KonanBuildService>
48 
49     @get:Nested abstract val clangParameters: ClangCompileParameters
50 
51     @TaskAction
compilenull52     fun compile() {
53         workerExecutor.noIsolation().submit(ClangCompileWorker::class.java) {
54             it.buildService.set(konanBuildService)
55             it.clangParameters.set(clangParameters)
56         }
57     }
58 }
59 
60 abstract class ClangCompileParameters {
61     /** The compilation target platform for which the given inputs will be compiled. */
62     @get:Input abstract val konanTarget: Property<SerializableKonanTarget>
63 
64     /** List of C source files. */
65     @get:InputFiles
66     @get:PathSensitive(PathSensitivity.NAME_ONLY)
67     abstract val sources: ConfigurableFileCollection
68 
69     /** The output directory where the object files for each source file will be written. */
70     @get:OutputDirectory abstract val output: DirectoryProperty
71 
72     /** List of directories that include the headers used in the compilation. */
73     @get:InputFiles
74     @get:PathSensitive(PathSensitivity.NONE)
75     abstract val includes: ConfigurableFileCollection
76 
77     /** List of arguments that will be passed into clang during compilation. */
78     @get:Input abstract val freeArgs: ListProperty<String>
79 }
80 
81 private abstract class ClangCompileWorker : WorkAction<ClangCompileWorker.Params> {
82     interface Params : WorkParameters {
83         val clangParameters: Property<ClangCompileParameters>
84         val buildService: Property<KonanBuildService>
85     }
86 
executenull87     override fun execute() {
88         val buildService = parameters.buildService.get()
89         buildService.compile(parameters.clangParameters.get())
90     }
91 }
92