diff options
-rw-r--r-- | BUILD | 25 | ||||
-rw-r--r-- | bazel/defs.bzl | 170 |
2 files changed, 192 insertions, 3 deletions
@@ -1,6 +1,24 @@ -licenses(["notice"]) +load("@rules_license//rules:license.bzl", "license") +load("@rules_license//rules:license_kind.bzl", "license_kind") -exports_files(["LICENSE"]) +package( + default_applicable_licenses = [":license"], + default_visibility = ["//visibility:public"], +) + +license( + name = "license", + license_kinds = [ + ":SPDX-license-identifier-BSD-2.0", + ], + visibility = [":__subpackages__"], +) + +license_kind( + name = "SPDX-license-identifier-BSD-2.0", + conditions = ["notice"], + url = "https://spdx.org/licenses/BSD-2-Clause.html", +) INCLUDES = [ ".", @@ -13,6 +31,7 @@ INCLUDES = [ COPTS = select({ ":windows": [], + "@platforms//os:windows": [], "//conditions:default": [ "-w", "-DHAVE_CONFIG_H", @@ -114,6 +133,7 @@ cc_library( ]), copts = COPTS, includes = INCLUDES, + visibility = ["//visibility:private"], ) cc_binary( @@ -124,7 +144,6 @@ cc_binary( ], copts = COPTS, includes = INCLUDES, - visibility = ["@libjpeg_turbo//:__pkg__"], deps = [ ":nasm_lib", ], diff --git a/bazel/defs.bzl b/bazel/defs.bzl new file mode 100644 index 00000000..3937a752 --- /dev/null +++ b/bazel/defs.bzl @@ -0,0 +1,170 @@ +"""Bazel Rules for Compiling NASM Assembly Code + +This module provides Bazel rules and functions to facilitate the compilation of +NASM assembly code within Bazel projects. It offers: + +- `nasm_compile`: A rule for compiling a single NASM source file into an object file. +- `nasm_library`: A macro for building static libraries from multiple NASM source files. + +Usage: + +```starlark +load("@nasm/bazel:defs.bzl", "nasm_compile", "nasm_library") + +# Compile a single .asm file +nasm_compile( + name = "my_object", + src = "my_code.asm", + out = "my_code.o", + output_format = "elf64", # Or "win64", "macho64" + # ... other attributes +) + +# Build a library from multiple .asm files +nasm_library( + name = "my_library", + srcs = ["code1.asm", "code2.asm"], + output_format = "elf64", + # ... other attributes +) +""" + +def _invoke_nasm(ctx, input_file, output_file, output_format, copts, includes): + """Executes the NASM assembler to compile an assembly file. + + Args: + ctx: The Bazel rule context. + input_file: The input assembly file. + output_file: The output object file. + output_format: The desired output format (e.g., "win64", "elf64", "macho64"). + copts: Additional compiler options as a list of strings. + includes: Include directories as a list of strings. + """ + + valid_formats = ["win64", "elf64", "macho64"] + if output_format not in valid_formats: + fail("Invalid output_format: {}. Must be one of {}".format(output_format, valid_formats)) + + args = [ + "-f", + output_format, + input_file.path, + "-o", + output_file.path, + ] + copts # Add any additional compiler options + + # Include directories + for include_label in includes: + include_path = "/".join([s for s in ( + ctx.label.workspace_root, + ctx.label.package, + include_label, + ) if s]) + args.extend(["-I", include_path]) + + ctx.actions.run( + inputs = [ctx.executable._nasm, input_file] + ctx.files.hdrs, + outputs = [output_file], + executable = ctx.executable._nasm, + arguments = args, + ) + +def _nasm_compile_impl(ctx): + """Bazel rule implementation for compiling a single NASM source file. + + This rule takes a NASM source file and produces a corresponding object file. + + Attributes: + src: The input NASM source file. + out: The output object file. + hdrs: Header files to include (optional). + includes: Include directories (optional). + output_format: Target output format. + copts: Additional compiler options. + """ + input_file = ctx.file.src + output_file = ctx.outputs.out + + _invoke_nasm( + ctx, + input_file, + output_file, + ctx.attr.output_format, + ctx.attr.copts, + ctx.attr.includes, + ) + +nasm_compile = rule( + implementation = _nasm_compile_impl, + attrs = { + "src": attr.label( + mandatory = True, + allow_single_file = True, + doc = "The NASM source file to be compiled.", + ), + "out": attr.output( + mandatory = True, + doc = "The output object file generated by the compilation.", + ), + "hdrs": attr.label_list( + allow_files = True, + doc = """A list of header files to be included during compilation. + These files are expected to be in the same directory as the source file or in the include directories.""", + ), + "includes": attr.string_list( + doc = """A list of include directories to search for header files. + These paths are relative to the workspace root or the current package, depending on the rule context.""", + ), + "output_format": attr.string( + mandatory = True, + values = ["win64", "elf64", "macho64"], + doc = "The target output format for the object file. Valid values are 'win64', 'elf64', and 'macho64'.", + ), + "copts": attr.string_list( + doc = "Additional options to pass to the NASM compiler.", + ), + "_nasm": attr.label( + default = Label("//:nasm"), + executable = True, + cfg = "exec", + doc = """The label pointing to the NASM executable. + This attribute is generally for internal use and rarely needs to be modified.""", + ), + }, + fragments = ["cpp"], +) + +def nasm_library(name, srcs, output_format, hdrs = None, includes = None): + """Builds a static library from NASM source files. + + Args: + name: The name of the library target. + srcs: A list of NASM source files to compile. + output_format: The target output format (e.g., "win64", "elf64", "macho64"). + hdrs: Optional header files to include in the library. + includes: Optional include directories for the compilation. + """ + + if not hdrs: + hdrs = [] + if not includes: + includes = [] + + src_deps = [] + for src in srcs: + obj_name = src.replace(".", "_").replace("/", "_") + ".o" + src_deps.append(obj_name) + nasm_compile( + name = "gen_" + obj_name, + src = src, + out = obj_name, + hdrs = hdrs, + includes = includes, + output_format = output_format, + ) + native.cc_library( + name = name, + srcs = src_deps, + hdrs = hdrs, + linkstatic = 1, + ) |