diff --git a/.bazelrc b/.bazelrc new file mode 100644 index 0000000..e69de29 diff --git a/.bazelversion b/.bazelversion new file mode 100644 index 0000000..ba7f754 --- /dev/null +++ b/.bazelversion @@ -0,0 +1 @@ +7.4.0 diff --git a/.github/actions/gitlint/action.yml b/.github/actions/gitlint/action.yml new file mode 100644 index 0000000..d1a190c --- /dev/null +++ b/.github/actions/gitlint/action.yml @@ -0,0 +1,21 @@ +name: "Gitlint Action" +description: "An action to install and run Gitlint on PR commits" +inputs: + pr-number: + description: "Pull Request number used to fetch commits" + required: true + base-branch: + description: "Base branch to compare commits against (default: origin/main)" + default: "origin/main" + required: false +runs: + using: "docker" + image: "jorisroovers/gitlint:0.19.1" + entrypoint: /bin/sh + args: + - -c + - | + git config --global --add safe.directory /github/workspace && \ + git fetch origin +refs/heads/main:refs/remotes/origin/main && \ + git fetch origin +refs/pull/${{ inputs.pr-number }}/head && \ + gitlint --commits origin/main..HEAD diff --git a/.github/workflows/copyright.yml b/.github/workflows/copyright.yml new file mode 100644 index 0000000..4315b26 --- /dev/null +++ b/.github/workflows/copyright.yml @@ -0,0 +1,17 @@ +name: Copyright checks +on: + pull_request: + types: [opened, reopened, synchronize] + merge_group: + types: [checks_requested] +jobs: + copyright-check: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4.2.2 + - name: Setup Bazel + uses: bazel-contrib/setup-bazel@0.9.1 + - name: Run copyright checks + run: | + bazel run //:copyright.check diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml new file mode 100644 index 0000000..2959f5d --- /dev/null +++ b/.github/workflows/docs.yml @@ -0,0 +1,60 @@ +name: Documentation build +on: + pull_request: + types: [opened, reopened, synchronize] + push: + branches: + - main + merge_group: + types: [checks_requested] +jobs: + docs-build: + runs-on: ubuntu-latest + permissions: + pull-requests: write + steps: + - name: Checkout repository + uses: actions/checkout@v4.2.2 + - name: Setup Bazel + uses: bazel-contrib/setup-bazel@0.9.1 + - name: Build documentation + run: | + bazel build //docs:github-pages && cp bazel-bin/docs/github-pages.tar . + - name: Upload artifact for deployment + if: github.event_name == 'push' && github.ref == 'refs/heads/main' + uses: actions/upload-artifact@v4.4.0 + with: + name: github-pages + path: ${{ github.workspace }}/github-pages.tar + retention-days: 1 + if-no-files-found: error + - name: Upload artifact for pull request link + if: github.event_name == 'pull_request' + id: upload-artifact-pr + uses: actions/upload-artifact@v4.4.0 + with: + name: github-pages-${{ github.sha }} + path: ${{ github.workspace }}/github-pages.tar + retention-days: 1 + if-no-files-found: error + - name: Comment artifact URL + if: github.event_name == 'pull_request' + run: | + gh pr comment ${{ github.event.pull_request.number }} \ + --body "Documentation artifact: ${{ steps.upload-artifact-pr.outputs.artifact-url }}" + env: + GH_TOKEN: ${{ github.token }} + docs-deploy: + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + permissions: + pages: write + id-token: write + runs-on: ubuntu-latest + if: github.event_name == 'push' && github.ref == 'refs/heads/main' + needs: docs-build + steps: + - name: Deploy to GitHub Pages + id: deployment + uses: actions/deploy-pages@v4.0.5 diff --git a/.github/workflows/format.yml b/.github/workflows/format.yml new file mode 100644 index 0000000..6cf2b38 --- /dev/null +++ b/.github/workflows/format.yml @@ -0,0 +1,17 @@ +name: Formatting checks +on: + pull_request: + types: [opened, reopened, synchronize] + merge_group: + types: [checks_requested] +jobs: + formatting-check: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4.2.2 + - name: Setup Bazel + uses: bazel-contrib/setup-bazel@0.9.1 + - name: Run formatting checks + run: | + bazel test //:format.check diff --git a/.github/workflows/gitlint.yml b/.github/workflows/gitlint.yml new file mode 100644 index 0000000..ae7d067 --- /dev/null +++ b/.github/workflows/gitlint.yml @@ -0,0 +1,19 @@ +name: Gitlint check +on: + pull_request: + types: [opened, synchronize, reopened] +jobs: + lint-commits: + name: check-commit-messages + runs-on: ubuntu-latest + steps: + - name: Checkout code + uses: actions/checkout@v3 + with: + fetch-depth: 0 + - name: Run Gitlint Action + if: ${{ github.event_name == 'pull_request' }} + uses: ./.github/actions/gitlint + with: + pr-number: ${{ github.event.number }} + base-branch: ${{ github.event.pull_request.base.ref }} diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..6c272ca --- /dev/null +++ b/.gitignore @@ -0,0 +1,6 @@ +# Bazel +bazel-* +MODULE.bazel.lock + +# Ruff +.ruff_cache diff --git a/.gitlint b/.gitlint new file mode 100644 index 0000000..53a3c5c --- /dev/null +++ b/.gitlint @@ -0,0 +1,42 @@ +# Available rules: +# +# T1: title-max-length +# T2: title-trailing-whitespace +# T3: title-trailing-punctuation (disabled) +# T4: title-hard-tab +# T5: title-must-not-contain-word (disabled) +# T6: title-leading-whitespace +# T7: title-match-regex (disabled) +# B1: body-max-line-length +# B2: body-trailing-whitespace +# B3: body-hard-tab +# B4: body-first-line-empty +# B5: body-min-length (disabled) +# B6: body-is-missing (disabled) +# B7: body-changed-file-mention (disabled) +# +# See http://jorisroovers.github.io/gitlint/rules/ for a full description. + +# Ignore some default rules and enable regex style searching +[general] +ignore=T3,T5,B1,B5,B7 +regex-style-search=true + +# Maximum length of the title +[title-max-length] +line-length=72 + +[title-match-regex] +regex=^[a-z_-]+: .+$ + +# First line of the commit message body must be empty. (second line of the commit message) +[body-first-line-empty] + +# Body must contain a reference to an issue +# 'see' will act as a form of reference from commits to issues without closing them. +[body-match-regex] +regex=Issue-ref: (see|close|closes|closed|fix|fixes|fixed|resolve|resolves|resolved) #(\d+) + +#Ignores the title if it starts with Revert or Merge +[ignore-by-title] +regex=(^Revert |^Merge ) diff --git a/BUILD b/BUILD new file mode 100644 index 0000000..946c504 --- /dev/null +++ b/BUILD @@ -0,0 +1,48 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +test_suite( + name = "format.check", + tests = ["//tools/format:format.check"], +) + +alias( + name = "format.fix", + actual = "//tools/format:format.fix", +) + +alias( + name = "copyright.check", + actual = "//tools/cr_checker:copyright.check", +) + +alias( + name = "copyright.fix", + actual = "//tools/cr_checker:copyright.fix", +) + +filegroup( + name = "repo_directories", + srcs = [ + "docs", + "tools", + ], + visibility = [ + "//tools/cr_checker:__subpackages__", + ], +) + +exports_files([ + "MODULE.bazel", + "BUILD", +]) diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..5278bc9 --- /dev/null +++ b/LICENSE @@ -0,0 +1,13 @@ +Copyright 2024 Contributors to the Eclipse Foundation + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. diff --git a/MODULE.bazel b/MODULE.bazel new file mode 100644 index 0000000..4d9f2cc --- /dev/null +++ b/MODULE.bazel @@ -0,0 +1,56 @@ +module( + name = "score_platform", + version = "0.1", + compatibility_level = 0, +) + +############################################################################### +# +# Python version +# +############################################################################### +bazel_dep(name = "rules_python", version = "0.37.2") + +PYTHON_VERSION = "3.12" + +python = use_extension("@rules_python//python/extensions:python.bzl", "python") +python.toolchain( + is_default = True, + python_version = PYTHON_VERSION, +) +use_repo(python) + +############################################################################### +# +# pip dependencies +# +############################################################################### +pip = use_extension("@rules_python//python/extensions:pip.bzl", "pip") +pip.parse( + hub_name = "pip_sphinx", + python_version = PYTHON_VERSION, + requirements_lock = "//docs:requirements_lock.txt", +) +use_repo(pip, "pip_sphinx") + +############################################################################### +# +# Packaging dependencies +# +############################################################################### +bazel_dep(name = "rules_pkg", version = "1.0.1") + +############################################################################### +# +# Buildifier dependency +# Provides formatting and linting of Bazel files. +# +############################################################################### +bazel_dep(name = "buildifier_prebuilt", version = "7.3.1") + +############################################################################### +# +# Generic linting and formatting rules +# +############################################################################### +bazel_dep(name = "aspect_rules_lint", version = "1.0.3") diff --git a/NOTICE b/NOTICE new file mode 100644 index 0000000..9ba2a49 --- /dev/null +++ b/NOTICE @@ -0,0 +1,35 @@ +# Notices for Eclipse Score + +This content is produced and maintained by the Eclipse Score project. + + * Project home: https://projects.eclipse.org/projects/automotive.score + +## Trademarks + +Eclipse Score and Score are trademarks of the Eclipse Foundation. +Eclipse, and the Eclipse Logo are registered trademarks of +the Eclipse Foundation. + +## Copyright + +All content is the property of the respective authors or their employers. +For more information regarding authorship of content, please consult the +listed source code repository logs. + +## Declared Project Licenses + +This program and the accompanying materials are made available under the terms +of the Apache License Version 2.0 which is available at +https://www.apache.org/licenses/LICENSE-2.0. + +SPDX-License-Identifier: Apache-2.0 + +## Source Code + +The project maintains the following source code repositories: + + * TBD + +## Third party Content + +TBD diff --git a/README.md b/README.md index 7f23687..f90f11e 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,29 @@ -# eclipse-score.github.io -The landing page website for the Score project +# Score landing page + +## Building + +### Supported environment +The build currently supports Linux environments. + +### Use bazelisk for bazel version management +Follow [instructions](https://github.com/bazelbuild/bazelisk) and setup bazelisk to manage your bazel version based on the .bazelversion file. + +### Check and fix formatting +``` +$ bazel test //:format.check +$ bazel run //:format.fix +``` + +## Documentation + +Use //docs:docs target to build the documentation. +``` +$ bazel build //docs:docs +``` + +The output directory can be found under ```bazel-bin/docs/docs/_build/html```. + +If you need to update pip dependencies, after modifying the requirements file, regenerate the lock file: +``` +bazel run //docs:requirements.update +``` diff --git a/docs/BUILD b/docs/BUILD new file mode 100644 index 0000000..baa5b2e --- /dev/null +++ b/docs/BUILD @@ -0,0 +1,74 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +load("@pip_sphinx//:requirements.bzl", "requirement") +load("@rules_pkg//pkg:mappings.bzl", "pkg_files") +load("@rules_pkg//pkg:tar.bzl", "pkg_tar") +load("@rules_python//python:defs.bzl", "py_library") +load("@rules_python//python:pip.bzl", "compile_pip_requirements") +load("@rules_python//sphinxdocs:sphinx.bzl", "sphinx_build_binary", "sphinx_docs") + +sphinx_docs( + name = "docs", + srcs = glob([ + "**/*.png", + "**/*.svg", + "**/*.rst", + "**/*.html", + ]), + config = ":conf.py", + extra_opts = [ + "-W", + "--keep-going", + ], + formats = [ + "html", + ], + sphinx = ":sphinx_build", + tags = [ + "manual", + ], +) + +sphinx_build_binary( + name = "sphinx_build", + deps = [ + requirement("sphinx"), + ], +) + +compile_pip_requirements( + name = "requirements", + src = "requirements.txt", + requirements_txt = "requirements_lock.txt", + tags = [ + "manual", + ], +) + +filegroup( + name = "html", + srcs = [":docs"], + output_group = "html", +) + +pkg_files( + name = "html_files", + srcs = [":html"], + renames = {"html": ""}, +) + +pkg_tar( + name = "github-pages", + srcs = [":html_files"], +) diff --git a/docs/_assets/score_architecture_core_stack_target_picture.png b/docs/_assets/score_architecture_core_stack_target_picture.png new file mode 100644 index 0000000..18ee805 Binary files /dev/null and b/docs/_assets/score_architecture_core_stack_target_picture.png differ diff --git a/docs/_assets/score_architecture_high_level_overview.png b/docs/_assets/score_architecture_high_level_overview.png new file mode 100644 index 0000000..5210eb0 Binary files /dev/null and b/docs/_assets/score_architecture_high_level_overview.png differ diff --git a/docs/_assets/score_roadmap.svg b/docs/_assets/score_roadmap.svg new file mode 100644 index 0000000..a36af21 --- /dev/null +++ b/docs/_assets/score_roadmap.svg @@ -0,0 +1,4 @@ + + + +
Project set-up
Release v0.1
Definition v1.0

Release v0.5
Release v1.0
Dec, 2024
Beginning of 2025
Mid of 2025
End of 2025
2026
MVP Phase
Alignment Phase
Development Phase
Product Versions based on SCORE Release 1.x
Release v1.x
Series Stability & Evolution Phase
2030
  • Creation of SCORE project in Eclipse SDV
  • Initial set-up of toolchain and infrastructure
  • ASIL Software Development process is defined
  • Proof of automotive grade "Qualification ability" (Safety Audit)
  • Definition of platform architecture and feature requirements for SCORE v1.0
  • Provides first public implementation of the most important modules, e.g. IPC, that can be used to build first distributions
  • SCORE v1.0 release should contain all common modules of an autonomous driving platform
\ No newline at end of file diff --git a/docs/_assets/score_tooling.svg b/docs/_assets/score_tooling.svg new file mode 100644 index 0000000..8e72c95 --- /dev/null +++ b/docs/_assets/score_tooling.svg @@ -0,0 +1,4 @@ + + + +
Component
Detailed Design
Feature 
Requirements & 
Architecture
Stakeholder 
Requirements
Verification
Implementation
ITF
[Integration Testing
Framework]
DrawIO
powered by
Bazel
SW Unit
Verification
Component 
Requirements & 
Architecture
PlantUML
\ No newline at end of file diff --git a/docs/_templates/layout.html b/docs/_templates/layout.html new file mode 100644 index 0000000..c6794ac --- /dev/null +++ b/docs/_templates/layout.html @@ -0,0 +1,8 @@ +{% extends "!layout.html" %} + {% block footer %} {{ super() }} + + + +{% endblock %} diff --git a/docs/conf.py b/docs/conf.py new file mode 100644 index 0000000..e08df38 --- /dev/null +++ b/docs/conf.py @@ -0,0 +1,38 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +# Configuration file for the Sphinx documentation builder. +# +# For the full list of built-in configuration values, see the documentation: +# https://www.sphinx-doc.org/en/master/usage/configuration.html + +# -- Project information ----------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#project-information + +project = "SCORE" +copyright = "2024, Score" +author = "SCORE committers" +release = "0.1" + +# -- General configuration --------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#general-configuration + +templates_path = ["_templates"] + +numfig = True + +# -- Options for HTML output ------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#options-for-html-output + +html_theme = "alabaster" +html_theme_options = {"page_width": "auto", "body_max_width": "1500"} diff --git a/docs/index.rst b/docs/index.rst new file mode 100644 index 0000000..094d90a --- /dev/null +++ b/docs/index.rst @@ -0,0 +1,188 @@ +.. + # ******************************************************************************* + # Copyright (c) 2024 Contributors to the Eclipse Foundation + # + # See the NOTICE file(s) distributed with this work for additional + # information regarding copyright ownership. + # + # This program and the accompanying materials are made available under the + # terms of the Apache License Version 2.0 which is available at + # https://www.apache.org/licenses/LICENSE-2.0 + # + # SPDX-License-Identifier: Apache-2.0 + # ******************************************************************************* + +SCORE (Eclipse Safe Open Vehicle Core) +###################################### + +Background +********** + +With the upcoming of central EE architectures in vehicles, computing power has been upgraded on few central components called 'High Performance Computers' or HPC. Together with these computing units comes an upgrade of operating systems towards multi-threaded schedulers with memory and resource separation in processes. There is a gap between these operating systems and the application layer that requires a common interface with functions and features for applications and application domains. The sum of these common and domain-agnostic functions is generally called "Middleware". The project uses the term "Core Software Stack" for this kind of functionality in differentiation to domain specific software stacks. + +Scope +***** + +The scope of this project is the development of an open source core stack for Software Defined Vehicles (SDVs), specifically targeting embedded high-performance Electronic Control Units (ECUs). + +Safe Open Vehicle Core is targeting to be the non-differentiating core of a software stack running on HPC ECUs of a software-defined vehicle. Consequently, this project's scope are the "inner layers" of such a stack between a hardware abstraction as its 'lower bound', 'southbound interface' and a platform API towards vehicle function applications as its 'upper bound', 'northbound interface'. + +Out of scope are said applications running on this stack (those carry the differentiating aspects covered by adopters of the stack). As well out of scope are any aspects related to a concrete hardware target, which will be freely chosen by each adopter individually, as per the needs of and as they see fit with their vehicle architecture — except support for a potential reference hardware. Furthermore, any off-board functionality (e.g. cloud services) is considered out of scope. Looking beyond mere implementations in code, the project very well considers establishing concepts and implementations of processes, or a "way of doing things", or best practices to be in scope — but only as long as it pertains to making code fit for automotive grade. + +Guiding Principles +****************** +The project aims to BUILD THE BEST AUTOMOTIVE RUNTIME SOLUTION ONLY ONCE. To achieve this, it is guided by several key principles. + +Common Stack & Industry-Wide Collaboration +========================================== + + The Safe Open Vehicle Core project aims to create a common full stack solution of a software runtime that serves as the best possible solution for shared industry problems. By achieving efficiencies through a single, joint solution instead of multiple specific ones, the project addresses non-differentiating scopes and ensures that the scope is significant for multiple parties, rather than catering to singular interests. + +Speed +===== + + The project accelerates development by working in open source, focusing on code-centric and iterative methods rather than primarily on textual specifications. + +Abstraction and Extensibility +============================= + + The project emphasizes the decoupling of hardware (HW) and software (SW), ensuring that applications do not depend on specific hardware characteristics. It establishes predetermined breaking points to enable the exchange of implementations of individual layers, aspects, and components, such as ECU communication protocols. Additionally, it focuses on enabling project-specific extensions of the stack, providing a flexible framework that can be customized and extended to meet the specific requirements of different projects. + +Quality & Efficiency +==================== + + The Safe Open Vehicle Core project aims for a lean, no-frills solution to lower complexity and increase efficiency. The project strives for support of modern implementation paradigms and languages like Rust or C++, uses human-readable specification languages that are domain and target-driven, and avoids complex exchange data formats. It seeks the optimal balance between modularity and resource consumption and follows state-of-the-art processes to develop safe and secure software in an open source environment. + + + +By achieving these goals and adhering to these key principles, the Safe Open Vehicle Core Project aims to deliver a versatile, safe and secure core stack that supports the evolving needs of the automotive industry and accelerates the adoption of software-defined vehicle technologies. + +Architecture +************ + +The following figures show a draft version of the planned architecture of the core stack. The architecture will be refined further as part of the project. + +High Level View on the Core Stack +================================= + +The following high level architecture picture gives you an overview of the main platform building blocks +including hardware specific peripherals. + + .. image:: _assets/score_architecture_high_level_overview.png + :width: 900 + :alt: High level view on the core stack + :align: center + +Target Picture of Core Stack - PRELIMINARY +========================================== + +The following image shows platform architecture in more details including surroundings as +Board support package (BSP) and HW specific. + + .. image:: _assets/score_architecture_core_stack_target_picture.png + :width: 900 + :alt: Target picture the core stack (preliminary) + :align: center + +Infrastructure +************** + +The tooling used in this project is depicted in the following figure. + + .. image:: _assets/score_tooling.svg + :width: 600 + :alt: Infrastructure overview + :align: center + +In general, all tooling is made available as open source and comes either from other open source projects +or is developed in the context of the *SCORE* project. The whole infrastructure is based on a build system called +`bazel `_. All workflows such as cloning the repositories, building the software, +generation of documentation, testing and much more are automated using bazel. This provides every project user with +the same user experience. To start working with bazel in the *SCORE* project, you should check +this `introduction page `_. + +For documenting the process, requirements and architecture we rely on `sphinx `_ and it's extension +`sphinx-needs `_. For small diagrams we use `PlantUML sphinx-needs extensions `_, +for larger diagrams we use `draw.io `_. + +We support both C++ and Rust programming languages. Software development is done in both languages. Decision which language to choose is done during +architecture process. In general, C++ should be used only for the existing modules, that are taken over or referenced by the *SCORE* project. +For new features and components we aim to develop the code mostly in Rust, as it seems to be more suitable for development compliant to ISO 26262:2018. + +We use `gtest/gmock `_ for unit testing and *ITF (Integration testing framework)* for component and integration tests. +*ITF* was originally developed by one of the initial partners of the *SCORE* project and provided to the community as open source project. Integration tests +are executed both in virtual environment and on the reference hardware. + +Roadmap +******* + +Here you can find the preliminary roadmap of the project: + + .. image:: _assets/score_roadmap.svg + :alt: project roadmap + :align: center + + +Please be aware, that this roadmap will be also transfered to the `GitHub project `_. +Please follow this link to get the latest state of the planning. + +MVP Phase +========= + +The main goals of the *MVP Phase* are following: + +* establish a working infrastructure, that enables every developer of the project to specify + requirements and architecture, implement code and test it accordingly. +* set-up project structure, that covers all aspects of the open source software development including + cooperation between developers and teams, planning, creation of the roadmaps and coordination meetings. +* define a software development process compliant to ISO 26262:2018, that is a prerequiste for any other software development in the project. + +A lot of preparation was already done in the background, therefore we are quite optimistic to finish the *MVP Phase* +latest in the beginning of 2025. + +Alignment Phase +=============== + +In the *Alignment Phase* the main goal is to align on the feature architecture and requirements of the *SCORE Platform v1.0*. +Additionally it is important to define the roadmap and the order, in which the features should be implemented. + +Development Phase +================= + +The *Development Phase* is the phase, where the implementation of the main modules of the platform should happen. +The most important milestone here is the *Release v0.5*, that should contain the basic modules, e.g *IPC*. +The *Release v0.5* milestone will show, whether previously defined software development process will work and how big is the acceptance and +the interest of the automotive community to the project. + +Series Stability & Evolution Phase +================================== + +In this phase the project should be in an well established state and accepted by the community. Continious development +of the features is taking place. + +How we Work +*********** + +Meetings +======== + +The following regular meetings (and corresponding meeting minutes) are held as part of the project: + +- `Project Leader Circle `_ + +- `Technical Leader Circle `_ + +The dates will be announced via the score-dev@eclipse.org mailing list. + +We plan to start regular exchange in the scope of the *SCORE* project in December 2024. + +Partners +======== + +The people working in this project are listed `here `_. + + +How to contribute +================= + +For contribution How-To please check the contribution guide `contribution guide `_. diff --git a/docs/requirements.txt b/docs/requirements.txt new file mode 100644 index 0000000..91fbf5d --- /dev/null +++ b/docs/requirements.txt @@ -0,0 +1,4 @@ +--extra-index-url https://pypi.org/simple/ + +Sphinx==8.1.3 +sphinx-needs==4.1.0 diff --git a/docs/requirements_lock.txt b/docs/requirements_lock.txt new file mode 100644 index 0000000..7d8cb87 --- /dev/null +++ b/docs/requirements_lock.txt @@ -0,0 +1,375 @@ +# +# This file is autogenerated by pip-compile with Python 3.12 +# by the following command: +# +# bazel run //docs:requirements.update +# +--extra-index-url https://pypi.org/simple/ + +alabaster==0.7.16 \ + --hash=sha256:75a8b99c28a5dad50dd7f8ccdd447a121ddb3892da9e53d1ca5cca3106d58d65 \ + --hash=sha256:b46733c07dce03ae4e150330b975c75737fa60f0a7c591b6c8bf4928a28e2c92 + # via sphinx +attrs==24.2.0 \ + --hash=sha256:5cfb1b9148b5b086569baec03f20d7b6bf3bcacc9a42bebf87ffaaca362f6346 \ + --hash=sha256:81921eb96de3191c8258c199618104dd27ac608d9366f5e35d011eae1867ede2 + # via + # jsonschema + # referencing +babel==2.15.0 \ + --hash=sha256:08706bdad8d0a3413266ab61bd6c34d0c28d6e1e7badf40a2cebe67644e2e1fb \ + --hash=sha256:8daf0e265d05768bc6c7a314cf1321e9a123afc328cc635c18622a2f30a04413 + # via sphinx +certifi==2024.7.4 \ + --hash=sha256:5a1e7645bc0ec61a09e26c36f6106dd4cf40c6db3a1fb6352b0244e7fb057c7b \ + --hash=sha256:c198e21b1289c2ab85ee4e67bb4b4ef3ead0892059901a8d5b622f24a1101e90 + # via requests +charset-normalizer==3.3.2 \ + --hash=sha256:06435b539f889b1f6f4ac1758871aae42dc3a8c0e24ac9e60c2384973ad73027 \ + --hash=sha256:06a81e93cd441c56a9b65d8e1d043daeb97a3d0856d177d5c90ba85acb3db087 \ + --hash=sha256:0a55554a2fa0d408816b3b5cedf0045f4b8e1a6065aec45849de2d6f3f8e9786 \ + --hash=sha256:0b2b64d2bb6d3fb9112bafa732def486049e63de9618b5843bcdd081d8144cd8 \ + --hash=sha256:10955842570876604d404661fbccbc9c7e684caf432c09c715ec38fbae45ae09 \ + --hash=sha256:122c7fa62b130ed55f8f285bfd56d5f4b4a5b503609d181f9ad85e55c89f4185 \ + --hash=sha256:1ceae2f17a9c33cb48e3263960dc5fc8005351ee19db217e9b1bb15d28c02574 \ + --hash=sha256:1d3193f4a680c64b4b6a9115943538edb896edc190f0b222e73761716519268e \ + --hash=sha256:1f79682fbe303db92bc2b1136016a38a42e835d932bab5b3b1bfcfbf0640e519 \ + --hash=sha256:2127566c664442652f024c837091890cb1942c30937add288223dc895793f898 \ + --hash=sha256:22afcb9f253dac0696b5a4be4a1c0f8762f8239e21b99680099abd9b2b1b2269 \ + --hash=sha256:25baf083bf6f6b341f4121c2f3c548875ee6f5339300e08be3f2b2ba1721cdd3 \ + --hash=sha256:2e81c7b9c8979ce92ed306c249d46894776a909505d8f5a4ba55b14206e3222f \ + --hash=sha256:3287761bc4ee9e33561a7e058c72ac0938c4f57fe49a09eae428fd88aafe7bb6 \ + --hash=sha256:34d1c8da1e78d2e001f363791c98a272bb734000fcef47a491c1e3b0505657a8 \ + --hash=sha256:37e55c8e51c236f95b033f6fb391d7d7970ba5fe7ff453dad675e88cf303377a \ + --hash=sha256:3d47fa203a7bd9c5b6cee4736ee84ca03b8ef23193c0d1ca99b5089f72645c73 \ + --hash=sha256:3e4d1f6587322d2788836a99c69062fbb091331ec940e02d12d179c1d53e25fc \ + --hash=sha256:42cb296636fcc8b0644486d15c12376cb9fa75443e00fb25de0b8602e64c1714 \ + --hash=sha256:45485e01ff4d3630ec0d9617310448a8702f70e9c01906b0d0118bdf9d124cf2 \ + --hash=sha256:4a78b2b446bd7c934f5dcedc588903fb2f5eec172f3d29e52a9096a43722adfc \ + --hash=sha256:4ab2fe47fae9e0f9dee8c04187ce5d09f48eabe611be8259444906793ab7cbce \ + --hash=sha256:4d0d1650369165a14e14e1e47b372cfcb31d6ab44e6e33cb2d4e57265290044d \ + --hash=sha256:549a3a73da901d5bc3ce8d24e0600d1fa85524c10287f6004fbab87672bf3e1e \ + --hash=sha256:55086ee1064215781fff39a1af09518bc9255b50d6333f2e4c74ca09fac6a8f6 \ + --hash=sha256:572c3763a264ba47b3cf708a44ce965d98555f618ca42c926a9c1616d8f34269 \ + --hash=sha256:573f6eac48f4769d667c4442081b1794f52919e7edada77495aaed9236d13a96 \ + --hash=sha256:5b4c145409bef602a690e7cfad0a15a55c13320ff7a3ad7ca59c13bb8ba4d45d \ + --hash=sha256:6463effa3186ea09411d50efc7d85360b38d5f09b870c48e4600f63af490e56a \ + --hash=sha256:65f6f63034100ead094b8744b3b97965785388f308a64cf8d7c34f2f2e5be0c4 \ + --hash=sha256:663946639d296df6a2bb2aa51b60a2454ca1cb29835324c640dafb5ff2131a77 \ + --hash=sha256:6897af51655e3691ff853668779c7bad41579facacf5fd7253b0133308cf000d \ + --hash=sha256:68d1f8a9e9e37c1223b656399be5d6b448dea850bed7d0f87a8311f1ff3dabb0 \ + --hash=sha256:6ac7ffc7ad6d040517be39eb591cac5ff87416c2537df6ba3cba3bae290c0fed \ + --hash=sha256:6b3251890fff30ee142c44144871185dbe13b11bab478a88887a639655be1068 \ + --hash=sha256:6c4caeef8fa63d06bd437cd4bdcf3ffefe6738fb1b25951440d80dc7df8c03ac \ + --hash=sha256:6ef1d82a3af9d3eecdba2321dc1b3c238245d890843e040e41e470ffa64c3e25 \ + --hash=sha256:753f10e867343b4511128c6ed8c82f7bec3bd026875576dfd88483c5c73b2fd8 \ + --hash=sha256:7cd13a2e3ddeed6913a65e66e94b51d80a041145a026c27e6bb76c31a853c6ab \ + --hash=sha256:7ed9e526742851e8d5cc9e6cf41427dfc6068d4f5a3bb03659444b4cabf6bc26 \ + --hash=sha256:7f04c839ed0b6b98b1a7501a002144b76c18fb1c1850c8b98d458ac269e26ed2 \ + --hash=sha256:802fe99cca7457642125a8a88a084cef28ff0cf9407060f7b93dca5aa25480db \ + --hash=sha256:80402cd6ee291dcb72644d6eac93785fe2c8b9cb30893c1af5b8fdd753b9d40f \ + --hash=sha256:8465322196c8b4d7ab6d1e049e4c5cb460d0394da4a27d23cc242fbf0034b6b5 \ + --hash=sha256:86216b5cee4b06df986d214f664305142d9c76df9b6512be2738aa72a2048f99 \ + --hash=sha256:87d1351268731db79e0f8e745d92493ee2841c974128ef629dc518b937d9194c \ + --hash=sha256:8bdb58ff7ba23002a4c5808d608e4e6c687175724f54a5dade5fa8c67b604e4d \ + --hash=sha256:8c622a5fe39a48f78944a87d4fb8a53ee07344641b0562c540d840748571b811 \ + --hash=sha256:8d756e44e94489e49571086ef83b2bb8ce311e730092d2c34ca8f7d925cb20aa \ + --hash=sha256:8f4a014bc36d3c57402e2977dada34f9c12300af536839dc38c0beab8878f38a \ + --hash=sha256:9063e24fdb1e498ab71cb7419e24622516c4a04476b17a2dab57e8baa30d6e03 \ + --hash=sha256:90d558489962fd4918143277a773316e56c72da56ec7aa3dc3dbbe20fdfed15b \ + --hash=sha256:923c0c831b7cfcb071580d3f46c4baf50f174be571576556269530f4bbd79d04 \ + --hash=sha256:95f2a5796329323b8f0512e09dbb7a1860c46a39da62ecb2324f116fa8fdc85c \ + --hash=sha256:96b02a3dc4381e5494fad39be677abcb5e6634bf7b4fa83a6dd3112607547001 \ + --hash=sha256:9f96df6923e21816da7e0ad3fd47dd8f94b2a5ce594e00677c0013018b813458 \ + --hash=sha256:a10af20b82360ab00827f916a6058451b723b4e65030c5a18577c8b2de5b3389 \ + --hash=sha256:a50aebfa173e157099939b17f18600f72f84eed3049e743b68ad15bd69b6bf99 \ + --hash=sha256:a981a536974bbc7a512cf44ed14938cf01030a99e9b3a06dd59578882f06f985 \ + --hash=sha256:a9a8e9031d613fd2009c182b69c7b2c1ef8239a0efb1df3f7c8da66d5dd3d537 \ + --hash=sha256:ae5f4161f18c61806f411a13b0310bea87f987c7d2ecdbdaad0e94eb2e404238 \ + --hash=sha256:aed38f6e4fb3f5d6bf81bfa990a07806be9d83cf7bacef998ab1a9bd660a581f \ + --hash=sha256:b01b88d45a6fcb69667cd6d2f7a9aeb4bf53760d7fc536bf679ec94fe9f3ff3d \ + --hash=sha256:b261ccdec7821281dade748d088bb6e9b69e6d15b30652b74cbbac25e280b796 \ + --hash=sha256:b2b0a0c0517616b6869869f8c581d4eb2dd83a4d79e0ebcb7d373ef9956aeb0a \ + --hash=sha256:b4a23f61ce87adf89be746c8a8974fe1c823c891d8f86eb218bb957c924bb143 \ + --hash=sha256:bd8f7df7d12c2db9fab40bdd87a7c09b1530128315d047a086fa3ae3435cb3a8 \ + --hash=sha256:beb58fe5cdb101e3a055192ac291b7a21e3b7ef4f67fa1d74e331a7f2124341c \ + --hash=sha256:c002b4ffc0be611f0d9da932eb0f704fe2602a9a949d1f738e4c34c75b0863d5 \ + --hash=sha256:c083af607d2515612056a31f0a8d9e0fcb5876b7bfc0abad3ecd275bc4ebc2d5 \ + --hash=sha256:c180f51afb394e165eafe4ac2936a14bee3eb10debc9d9e4db8958fe36afe711 \ + --hash=sha256:c235ebd9baae02f1b77bcea61bce332cb4331dc3617d254df3323aa01ab47bd4 \ + --hash=sha256:cd70574b12bb8a4d2aaa0094515df2463cb429d8536cfb6c7ce983246983e5a6 \ + --hash=sha256:d0eccceffcb53201b5bfebb52600a5fb483a20b61da9dbc885f8b103cbe7598c \ + --hash=sha256:d965bba47ddeec8cd560687584e88cf699fd28f192ceb452d1d7ee807c5597b7 \ + --hash=sha256:db364eca23f876da6f9e16c9da0df51aa4f104a972735574842618b8c6d999d4 \ + --hash=sha256:ddbb2551d7e0102e7252db79ba445cdab71b26640817ab1e3e3648dad515003b \ + --hash=sha256:deb6be0ac38ece9ba87dea880e438f25ca3eddfac8b002a2ec3d9183a454e8ae \ + --hash=sha256:e06ed3eb3218bc64786f7db41917d4e686cc4856944f53d5bdf83a6884432e12 \ + --hash=sha256:e27ad930a842b4c5eb8ac0016b0a54f5aebbe679340c26101df33424142c143c \ + --hash=sha256:e537484df0d8f426ce2afb2d0f8e1c3d0b114b83f8850e5f2fbea0e797bd82ae \ + --hash=sha256:eb00ed941194665c332bf8e078baf037d6c35d7c4f3102ea2d4f16ca94a26dc8 \ + --hash=sha256:eb6904c354526e758fda7167b33005998fb68c46fbc10e013ca97f21ca5c8887 \ + --hash=sha256:eb8821e09e916165e160797a6c17edda0679379a4be5c716c260e836e122f54b \ + --hash=sha256:efcb3f6676480691518c177e3b465bcddf57cea040302f9f4e6e191af91174d4 \ + --hash=sha256:f27273b60488abe721a075bcca6d7f3964f9f6f067c8c4c605743023d7d3944f \ + --hash=sha256:f30c3cb33b24454a82faecaf01b19c18562b1e89558fb6c56de4d9118a032fd5 \ + --hash=sha256:fb69256e180cb6c8a894fee62b3afebae785babc1ee98b81cdf68bbca1987f33 \ + --hash=sha256:fd1abc0d89e30cc4e02e4064dc67fcc51bd941eb395c502aac3ec19fab46b519 \ + --hash=sha256:ff8fa367d09b717b2a17a052544193ad76cd49979c805768879cb63d9ca50561 + # via requests +docutils==0.20.1 \ + --hash=sha256:96f387a2c5562db4476f09f13bbab2192e764cac08ebbf3a34a95d9b1e4a59d6 \ + --hash=sha256:f08a4e276c3a1583a86dce3e34aba3fe04d02bba2dd51ed16106244e8a923e3b + # via sphinx +idna==3.7 \ + --hash=sha256:028ff3aadf0609c1fd278d8ea3089299412a7a8b9bd005dd08b9f8285bcb5cfc \ + --hash=sha256:82fee1fc78add43492d3a1898bfa6d8a904cc97d8427f683ed8e798d07761aa0 + # via requests +imagesize==1.4.1 \ + --hash=sha256:0d8d18d08f840c19d0ee7ca1fd82490fdc3729b7ac93f49870406ddde8ef8d8b \ + --hash=sha256:69150444affb9cb0d5cc5a92b3676f0b2fb7cd9ae39e947a5e11a36b4497cd4a + # via sphinx +jinja2==3.1.4 \ + --hash=sha256:4a3aee7acbbe7303aede8e9648d13b8bf88a429282aa6122a993f0ac800cb369 \ + --hash=sha256:bc5dd2abb727a5319567b7a813e6a2e7318c39f4f487cfe6c89c6f9c7d25197d + # via sphinx +jsonschema==4.23.0 \ + --hash=sha256:d71497fef26351a33265337fa77ffeb82423f3ea21283cd9467bb03999266bc4 \ + --hash=sha256:fbadb6f8b144a8f8cf9f0b89ba94501d143e50411a1278633f56a7acf7fd5566 + # via sphinx-needs +jsonschema-specifications==2024.10.1 \ + --hash=sha256:0f38b83639958ce1152d02a7f062902c41c8fd20d558b0c34344292d417ae272 \ + --hash=sha256:a09a0680616357d9a0ecf05c12ad234479f549239d0f5b55f3deea67475da9bf + # via jsonschema +markupsafe==2.1.5 \ + --hash=sha256:00e046b6dd71aa03a41079792f8473dc494d564611a8f89bbbd7cb93295ebdcf \ + --hash=sha256:075202fa5b72c86ad32dc7d0b56024ebdbcf2048c0ba09f1cde31bfdd57bcfff \ + --hash=sha256:0e397ac966fdf721b2c528cf028494e86172b4feba51d65f81ffd65c63798f3f \ + --hash=sha256:17b950fccb810b3293638215058e432159d2b71005c74371d784862b7e4683f3 \ + --hash=sha256:1f3fbcb7ef1f16e48246f704ab79d79da8a46891e2da03f8783a5b6fa41a9532 \ + --hash=sha256:2174c595a0d73a3080ca3257b40096db99799265e1c27cc5a610743acd86d62f \ + --hash=sha256:2b7c57a4dfc4f16f7142221afe5ba4e093e09e728ca65c51f5620c9aaeb9a617 \ + --hash=sha256:2d2d793e36e230fd32babe143b04cec8a8b3eb8a3122d2aceb4a371e6b09b8df \ + --hash=sha256:30b600cf0a7ac9234b2638fbc0fb6158ba5bdcdf46aeb631ead21248b9affbc4 \ + --hash=sha256:397081c1a0bfb5124355710fe79478cdbeb39626492b15d399526ae53422b906 \ + --hash=sha256:3a57fdd7ce31c7ff06cdfbf31dafa96cc533c21e443d57f5b1ecc6cdc668ec7f \ + --hash=sha256:3c6b973f22eb18a789b1460b4b91bf04ae3f0c4234a0a6aa6b0a92f6f7b951d4 \ + --hash=sha256:3e53af139f8579a6d5f7b76549125f0d94d7e630761a2111bc431fd820e163b8 \ + --hash=sha256:4096e9de5c6fdf43fb4f04c26fb114f61ef0bf2e5604b6ee3019d51b69e8c371 \ + --hash=sha256:4275d846e41ecefa46e2015117a9f491e57a71ddd59bbead77e904dc02b1bed2 \ + --hash=sha256:4c31f53cdae6ecfa91a77820e8b151dba54ab528ba65dfd235c80b086d68a465 \ + --hash=sha256:4f11aa001c540f62c6166c7726f71f7573b52c68c31f014c25cc7901deea0b52 \ + --hash=sha256:5049256f536511ee3f7e1b3f87d1d1209d327e818e6ae1365e8653d7e3abb6a6 \ + --hash=sha256:58c98fee265677f63a4385256a6d7683ab1832f3ddd1e66fe948d5880c21a169 \ + --hash=sha256:598e3276b64aff0e7b3451b72e94fa3c238d452e7ddcd893c3ab324717456bad \ + --hash=sha256:5b7b716f97b52c5a14bffdf688f971b2d5ef4029127f1ad7a513973cfd818df2 \ + --hash=sha256:5dedb4db619ba5a2787a94d877bc8ffc0566f92a01c0ef214865e54ecc9ee5e0 \ + --hash=sha256:619bc166c4f2de5caa5a633b8b7326fbe98e0ccbfacabd87268a2b15ff73a029 \ + --hash=sha256:629ddd2ca402ae6dbedfceeba9c46d5f7b2a61d9749597d4307f943ef198fc1f \ + --hash=sha256:656f7526c69fac7f600bd1f400991cc282b417d17539a1b228617081106feb4a \ + --hash=sha256:6ec585f69cec0aa07d945b20805be741395e28ac1627333b1c5b0105962ffced \ + --hash=sha256:72b6be590cc35924b02c78ef34b467da4ba07e4e0f0454a2c5907f473fc50ce5 \ + --hash=sha256:7502934a33b54030eaf1194c21c692a534196063db72176b0c4028e140f8f32c \ + --hash=sha256:7a68b554d356a91cce1236aa7682dc01df0edba8d043fd1ce607c49dd3c1edcf \ + --hash=sha256:7b2e5a267c855eea6b4283940daa6e88a285f5f2a67f2220203786dfa59b37e9 \ + --hash=sha256:823b65d8706e32ad2df51ed89496147a42a2a6e01c13cfb6ffb8b1e92bc910bb \ + --hash=sha256:8590b4ae07a35970728874632fed7bd57b26b0102df2d2b233b6d9d82f6c62ad \ + --hash=sha256:8dd717634f5a044f860435c1d8c16a270ddf0ef8588d4887037c5028b859b0c3 \ + --hash=sha256:8dec4936e9c3100156f8a2dc89c4b88d5c435175ff03413b443469c7c8c5f4d1 \ + --hash=sha256:97cafb1f3cbcd3fd2b6fbfb99ae11cdb14deea0736fc2b0952ee177f2b813a46 \ + --hash=sha256:a17a92de5231666cfbe003f0e4b9b3a7ae3afb1ec2845aadc2bacc93ff85febc \ + --hash=sha256:a549b9c31bec33820e885335b451286e2969a2d9e24879f83fe904a5ce59d70a \ + --hash=sha256:ac07bad82163452a6884fe8fa0963fb98c2346ba78d779ec06bd7a6262132aee \ + --hash=sha256:ae2ad8ae6ebee9d2d94b17fb62763125f3f374c25618198f40cbb8b525411900 \ + --hash=sha256:b91c037585eba9095565a3556f611e3cbfaa42ca1e865f7b8015fe5c7336d5a5 \ + --hash=sha256:bc1667f8b83f48511b94671e0e441401371dfd0f0a795c7daa4a3cd1dde55bea \ + --hash=sha256:bec0a414d016ac1a18862a519e54b2fd0fc8bbfd6890376898a6c0891dd82e9f \ + --hash=sha256:bf50cd79a75d181c9181df03572cdce0fbb75cc353bc350712073108cba98de5 \ + --hash=sha256:bff1b4290a66b490a2f4719358c0cdcd9bafb6b8f061e45c7a2460866bf50c2e \ + --hash=sha256:c061bb86a71b42465156a3ee7bd58c8c2ceacdbeb95d05a99893e08b8467359a \ + --hash=sha256:c8b29db45f8fe46ad280a7294f5c3ec36dbac9491f2d1c17345be8e69cc5928f \ + --hash=sha256:ce409136744f6521e39fd8e2a24c53fa18ad67aa5bc7c2cf83645cce5b5c4e50 \ + --hash=sha256:d050b3361367a06d752db6ead6e7edeb0009be66bc3bae0ee9d97fb326badc2a \ + --hash=sha256:d283d37a890ba4c1ae73ffadf8046435c76e7bc2247bbb63c00bd1a709c6544b \ + --hash=sha256:d9fad5155d72433c921b782e58892377c44bd6252b5af2f67f16b194987338a4 \ + --hash=sha256:daa4ee5a243f0f20d528d939d06670a298dd39b1ad5f8a72a4275124a7819eff \ + --hash=sha256:db0b55e0f3cc0be60c1f19efdde9a637c32740486004f20d1cff53c3c0ece4d2 \ + --hash=sha256:e61659ba32cf2cf1481e575d0462554625196a1f2fc06a1c777d3f48e8865d46 \ + --hash=sha256:ea3d8a3d18833cf4304cd2fc9cbb1efe188ca9b5efef2bdac7adc20594a0e46b \ + --hash=sha256:ec6a563cff360b50eed26f13adc43e61bc0c04d94b8be985e6fb24b81f6dcfdf \ + --hash=sha256:f5dfb42c4604dddc8e4305050aa6deb084540643ed5804d7455b5df8fe16f5e5 \ + --hash=sha256:fa173ec60341d6bb97a89f5ea19c85c5643c1e7dedebc22f5181eb73573142c5 \ + --hash=sha256:fa9db3f79de01457b03d4f01b34cf91bc0048eb2c3846ff26f66687c2f6d16ab \ + --hash=sha256:fce659a462a1be54d2ffcacea5e3ba2d74daa74f30f5f143fe0c58636e355fdd \ + --hash=sha256:ffee1f21e5ef0d712f9033568f8344d5da8cc2869dbd08d87c84656e6a2d2f68 + # via jinja2 +packaging==24.1 \ + --hash=sha256:026ed72c8ed3fcce5bf8950572258698927fd1dbda10a5e981cdf0ac37f4f002 \ + --hash=sha256:5b8f2217dbdbd2f7f384c41c628544e6d52f2d0f53c6d0c3ea61aa5d1d7ff124 + # via sphinx +pygments==2.18.0 \ + --hash=sha256:786ff802f32e91311bff3889f6e9a86e81505fe99f2735bb6d60ae0c5004f199 \ + --hash=sha256:b8e6aca0523f3ab76fee51799c488e38782ac06eafcf95e7ba832985c8e7b13a + # via sphinx +referencing==0.35.1 \ + --hash=sha256:25b42124a6c8b632a425174f24087783efb348a6f1e0008e63cd4466fedf703c \ + --hash=sha256:eda6d3234d62814d1c64e305c1331c9a3a6132da475ab6382eaa997b21ee75de + # via + # jsonschema + # jsonschema-specifications +requests==2.32.3 \ + --hash=sha256:55365417734eb18255590a9ff9eb97e9e1da868d4ccd6402399eaf68af20a760 \ + --hash=sha256:70761cfe03c773ceb22aa2f671b4757976145175cdfca038c02654d061d6dcc6 + # via + # requests-file + # sphinx + # sphinx-needs +requests-file==2.1.0 \ + --hash=sha256:0f549a3f3b0699415ac04d167e9cb39bccfb730cb832b4d20be3d9867356e658 \ + --hash=sha256:cf270de5a4c5874e84599fc5778303d496c10ae5e870bfa378818f35d21bda5c + # via sphinx-needs +rpds-py==0.21.0 \ + --hash=sha256:031819f906bb146561af051c7cef4ba2003d28cff07efacef59da973ff7969ba \ + --hash=sha256:0626238a43152918f9e72ede9a3b6ccc9e299adc8ade0d67c5e142d564c9a83d \ + --hash=sha256:085ed25baac88953d4283e5b5bd094b155075bb40d07c29c4f073e10623f9f2e \ + --hash=sha256:0a9e0759e7be10109645a9fddaaad0619d58c9bf30a3f248a2ea57a7c417173a \ + --hash=sha256:0c025820b78817db6a76413fff6866790786c38f95ea3f3d3c93dbb73b632202 \ + --hash=sha256:1ff2eba7f6c0cb523d7e9cff0903f2fe1feff8f0b2ceb6bd71c0e20a4dcee271 \ + --hash=sha256:20cc1ed0bcc86d8e1a7e968cce15be45178fd16e2ff656a243145e0b439bd250 \ + --hash=sha256:241e6c125568493f553c3d0fdbb38c74babf54b45cef86439d4cd97ff8feb34d \ + --hash=sha256:2c51d99c30091f72a3c5d126fad26236c3f75716b8b5e5cf8effb18889ced928 \ + --hash=sha256:2d6129137f43f7fa02d41542ffff4871d4aefa724a5fe38e2c31a4e0fd343fb0 \ + --hash=sha256:30b912c965b2aa76ba5168fd610087bad7fcde47f0a8367ee8f1876086ee6d1d \ + --hash=sha256:30bdc973f10d28e0337f71d202ff29345320f8bc49a31c90e6c257e1ccef4333 \ + --hash=sha256:320c808df533695326610a1b6a0a6e98f033e49de55d7dc36a13c8a30cfa756e \ + --hash=sha256:32eb88c30b6a4f0605508023b7141d043a79b14acb3b969aa0b4f99b25bc7d4a \ + --hash=sha256:3b766a9f57663396e4f34f5140b3595b233a7b146e94777b97a8413a1da1be18 \ + --hash=sha256:3b929c2bb6e29ab31f12a1117c39f7e6d6450419ab7464a4ea9b0b417174f044 \ + --hash=sha256:3e30a69a706e8ea20444b98a49f386c17b26f860aa9245329bab0851ed100677 \ + --hash=sha256:3e53861b29a13d5b70116ea4230b5f0f3547b2c222c5daa090eb7c9c82d7f664 \ + --hash=sha256:40c91c6e34cf016fa8e6b59d75e3dbe354830777fcfd74c58b279dceb7975b75 \ + --hash=sha256:4991ca61656e3160cdaca4851151fd3f4a92e9eba5c7a530ab030d6aee96ec89 \ + --hash=sha256:4ab2c2a26d2f69cdf833174f4d9d86118edc781ad9a8fa13970b527bf8236027 \ + --hash=sha256:4e8921a259f54bfbc755c5bbd60c82bb2339ae0324163f32868f63f0ebb873d9 \ + --hash=sha256:4eb2de8a147ffe0626bfdc275fc6563aa7bf4b6db59cf0d44f0ccd6ca625a24e \ + --hash=sha256:5145282a7cd2ac16ea0dc46b82167754d5e103a05614b724457cffe614f25bd8 \ + --hash=sha256:520ed8b99b0bf86a176271f6fe23024323862ac674b1ce5b02a72bfeff3fff44 \ + --hash=sha256:52c041802a6efa625ea18027a0723676a778869481d16803481ef6cc02ea8cb3 \ + --hash=sha256:5555db3e618a77034954b9dc547eae94166391a98eb867905ec8fcbce1308d95 \ + --hash=sha256:58a0e345be4b18e6b8501d3b0aa540dad90caeed814c515e5206bb2ec26736fd \ + --hash=sha256:590ef88db231c9c1eece44dcfefd7515d8bf0d986d64d0caf06a81998a9e8cab \ + --hash=sha256:5afb5efde74c54724e1a01118c6e5c15e54e642c42a1ba588ab1f03544ac8c7a \ + --hash=sha256:688c93b77e468d72579351a84b95f976bd7b3e84aa6686be6497045ba84be560 \ + --hash=sha256:6b4ef7725386dc0762857097f6b7266a6cdd62bfd209664da6712cb26acef035 \ + --hash=sha256:6bc0e697d4d79ab1aacbf20ee5f0df80359ecf55db33ff41481cf3e24f206919 \ + --hash=sha256:6dcc4949be728ede49e6244eabd04064336012b37f5c2200e8ec8eb2988b209c \ + --hash=sha256:6f54e7106f0001244a5f4cf810ba8d3f9c542e2730821b16e969d6887b664266 \ + --hash=sha256:808f1ac7cf3b44f81c9475475ceb221f982ef548e44e024ad5f9e7060649540e \ + --hash=sha256:8404b3717da03cbf773a1d275d01fec84ea007754ed380f63dfc24fb76ce4592 \ + --hash=sha256:878f6fea96621fda5303a2867887686d7a198d9e0f8a40be100a63f5d60c88c9 \ + --hash=sha256:8a7ff941004d74d55a47f916afc38494bd1cfd4b53c482b77c03147c91ac0ac3 \ + --hash=sha256:95a5bad1ac8a5c77b4e658671642e4af3707f095d2b78a1fdd08af0dfb647624 \ + --hash=sha256:97ef67d9bbc3e15584c2f3c74bcf064af36336c10d2e21a2131e123ce0f924c9 \ + --hash=sha256:98486337f7b4f3c324ab402e83453e25bb844f44418c066623db88e4c56b7c7b \ + --hash=sha256:98e4fe5db40db87ce1c65031463a760ec7906ab230ad2249b4572c2fc3ef1f9f \ + --hash=sha256:998a8080c4495e4f72132f3d66ff91f5997d799e86cec6ee05342f8f3cda7dca \ + --hash=sha256:9afe42102b40007f588666bc7de82451e10c6788f6f70984629db193849dced1 \ + --hash=sha256:9e20da3957bdf7824afdd4b6eeb29510e83e026473e04952dca565170cd1ecc8 \ + --hash=sha256:a017f813f24b9df929674d0332a374d40d7f0162b326562daae8066b502d0590 \ + --hash=sha256:a429b99337062877d7875e4ff1a51fe788424d522bd64a8c0a20ef3021fdb6ed \ + --hash=sha256:a58ce66847711c4aa2ecfcfaff04cb0327f907fead8945ffc47d9407f41ff952 \ + --hash=sha256:a78d8b634c9df7f8d175451cfeac3810a702ccb85f98ec95797fa98b942cea11 \ + --hash=sha256:a89a8ce9e4e75aeb7fa5d8ad0f3fecdee813802592f4f46a15754dcb2fd6b061 \ + --hash=sha256:a8eeec67590e94189f434c6d11c426892e396ae59e4801d17a93ac96b8c02a6c \ + --hash=sha256:aaeb25ccfb9b9014a10eaf70904ebf3f79faaa8e60e99e19eef9f478651b9b74 \ + --hash=sha256:ad116dda078d0bc4886cb7840e19811562acdc7a8e296ea6ec37e70326c1b41c \ + --hash=sha256:af04ac89c738e0f0f1b913918024c3eab6e3ace989518ea838807177d38a2e94 \ + --hash=sha256:af4a644bf890f56e41e74be7d34e9511e4954894d544ec6b8efe1e21a1a8da6c \ + --hash=sha256:b21747f79f360e790525e6f6438c7569ddbfb1b3197b9e65043f25c3c9b489d8 \ + --hash=sha256:b229ce052ddf1a01c67d68166c19cb004fb3612424921b81c46e7ea7ccf7c3bf \ + --hash=sha256:b4de1da871b5c0fd5537b26a6fc6814c3cc05cabe0c941db6e9044ffbb12f04a \ + --hash=sha256:b80b4690bbff51a034bfde9c9f6bf9357f0a8c61f548942b80f7b66356508bf5 \ + --hash=sha256:b876f2bc27ab5954e2fd88890c071bd0ed18b9c50f6ec3de3c50a5ece612f7a6 \ + --hash=sha256:b8f107395f2f1d151181880b69a2869c69e87ec079c49c0016ab96860b6acbe5 \ + --hash=sha256:b9b76e2afd585803c53c5b29e992ecd183f68285b62fe2668383a18e74abe7a3 \ + --hash=sha256:c2b2f71c6ad6c2e4fc9ed9401080badd1469fa9889657ec3abea42a3d6b2e1ed \ + --hash=sha256:c3761f62fcfccf0864cc4665b6e7c3f0c626f0380b41b8bd1ce322103fa3ef87 \ + --hash=sha256:c38dbf31c57032667dd5a2f0568ccde66e868e8f78d5a0d27dcc56d70f3fcd3b \ + --hash=sha256:ca9989d5d9b1b300bc18e1801c67b9f6d2c66b8fd9621b36072ed1df2c977f72 \ + --hash=sha256:cbd7504a10b0955ea287114f003b7ad62330c9e65ba012c6223dba646f6ffd05 \ + --hash=sha256:d167e4dbbdac48bd58893c7e446684ad5d425b407f9336e04ab52e8b9194e2ed \ + --hash=sha256:d2132377f9deef0c4db89e65e8bb28644ff75a18df5293e132a8d67748397b9f \ + --hash=sha256:da52d62a96e61c1c444f3998c434e8b263c384f6d68aca8274d2e08d1906325c \ + --hash=sha256:daa8efac2a1273eed2354397a51216ae1e198ecbce9036fba4e7610b308b6153 \ + --hash=sha256:dc5695c321e518d9f03b7ea6abb5ea3af4567766f9852ad1560f501b17588c7b \ + --hash=sha256:de552f4a1916e520f2703ec474d2b4d3f86d41f353e7680b597512ffe7eac5d0 \ + --hash=sha256:de609a6f1b682f70bb7163da745ee815d8f230d97276db049ab447767466a09d \ + --hash=sha256:e12bb09678f38b7597b8346983d2323a6482dcd59e423d9448108c1be37cac9d \ + --hash=sha256:e168afe6bf6ab7ab46c8c375606298784ecbe3ba31c0980b7dcbb9631dcba97e \ + --hash=sha256:e78868e98f34f34a88e23ee9ccaeeec460e4eaf6db16d51d7a9b883e5e785a5e \ + --hash=sha256:e860f065cc4ea6f256d6f411aba4b1251255366e48e972f8a347cf88077b24fd \ + --hash=sha256:ea3a6ac4d74820c98fcc9da4a57847ad2cc36475a8bd9683f32ab6d47a2bd682 \ + --hash=sha256:ebf64e281a06c904a7636781d2e973d1f0926a5b8b480ac658dc0f556e7779f4 \ + --hash=sha256:ed6378c9d66d0de903763e7706383d60c33829581f0adff47b6535f1802fa6db \ + --hash=sha256:ee1e4fc267b437bb89990b2f2abf6c25765b89b72dd4a11e21934df449e0c976 \ + --hash=sha256:ee4eafd77cc98d355a0d02f263efc0d3ae3ce4a7c24740010a8b4012bbb24937 \ + --hash=sha256:efec946f331349dfc4ae9d0e034c263ddde19414fe5128580f512619abed05f1 \ + --hash=sha256:f414da5c51bf350e4b7960644617c130140423882305f7574b6cf65a3081cecb \ + --hash=sha256:f71009b0d5e94c0e86533c0b27ed7cacc1239cb51c178fd239c3cfefefb0400a \ + --hash=sha256:f983e4c2f603c95dde63df633eec42955508eefd8d0f0e6d236d31a044c882d7 \ + --hash=sha256:faa5e8496c530f9c71f2b4e1c49758b06e5f4055e17144906245c99fa6d45356 \ + --hash=sha256:fed5dfefdf384d6fe975cc026886aece4f292feaf69d0eeb716cfd3c5a4dd8be + # via + # jsonschema + # referencing +snowballstemmer==2.2.0 \ + --hash=sha256:09b16deb8547d3412ad7b590689584cd0fe25ec8db3be37788be3810cbf19cb1 \ + --hash=sha256:c8e1716e83cc398ae16824e5572ae04e0d9fc2c6b985fb0f900f5f0c96ecba1a + # via sphinx +sphinx==8.1.3 \ + --hash=sha256:09719015511837b76bf6e03e42eb7595ac8c2e41eeb9c29c5b755c6b677992a2 \ + --hash=sha256:43c1911eecb0d3e161ad78611bc905d1ad0e523e4ddc202a58a821773dc4c927 + # via + # -r docs/requirements.txt + # sphinx-data-viewer + # sphinx-needs + # sphinxcontrib-jquery +sphinx-data-viewer==0.1.5 \ + --hash=sha256:a7d5e58613562bb745380bfe61ca8b69997998167fd6fa9aea55606c9a4b17e4 \ + --hash=sha256:b74b1d304c505c464d07c7b225ed0d84ea02dcc88bc1c49cdad7c2275fbbdad4 + # via sphinx-needs +sphinx-needs==4.1.0 \ + --hash=sha256:7d40e9c29353d9784f469b2093412846060cda4f3b55127ac58a2692c3381ef9 \ + --hash=sha256:8ae21e10515249aaba3dabd7fd66afdedd1160ecbc5816337fb6ed82aca293b7 + # via -r docs/requirements.txt +sphinxcontrib-applehelp==1.0.8 \ + --hash=sha256:c40a4f96f3776c4393d933412053962fac2b84f4c99a7982ba42e09576a70619 \ + --hash=sha256:cb61eb0ec1b61f349e5cc36b2028e9e7ca765be05e49641c97241274753067b4 + # via sphinx +sphinxcontrib-devhelp==1.0.6 \ + --hash=sha256:6485d09629944511c893fa11355bda18b742b83a2b181f9a009f7e500595c90f \ + --hash=sha256:9893fd3f90506bc4b97bdb977ceb8fbd823989f4316b28c3841ec128544372d3 + # via sphinx +sphinxcontrib-htmlhelp==2.1.0 \ + --hash=sha256:166759820b47002d22914d64a075ce08f4c46818e17cfc9470a9786b759b19f8 \ + --hash=sha256:c9e2916ace8aad64cc13a0d233ee22317f2b9025b9cf3295249fa985cc7082e9 + # via sphinx +sphinxcontrib-jquery==4.1 \ + --hash=sha256:1620739f04e36a2c779f1a131a2dfd49b2fd07351bf1968ced074365933abc7a \ + --hash=sha256:f936030d7d0147dd026a4f2b5a57343d233f1fc7b363f68b3d4f1cb0993878ae + # via sphinx-needs +sphinxcontrib-jsmath==1.0.1 \ + --hash=sha256:2ec2eaebfb78f3f2078e73666b1415417a116cc848b72e5172e596c871103178 \ + --hash=sha256:a9925e4a4587247ed2191a22df5f6970656cb8ca2bd6284309578f2153e0c4b8 + # via sphinx +sphinxcontrib-qthelp==1.0.7 \ + --hash=sha256:053dedc38823a80a7209a80860b16b722e9e0209e32fea98c90e4e6624588ed6 \ + --hash=sha256:e2ae3b5c492d58fcbd73281fbd27e34b8393ec34a073c792642cd8e529288182 + # via sphinx +sphinxcontrib-serializinghtml==1.1.10 \ + --hash=sha256:326369b8df80a7d2d8d7f99aa5ac577f51ea51556ed974e7716cfd4fca3f6cb7 \ + --hash=sha256:93f3f5dc458b91b192fe10c397e324f262cf163d79f3282c158e8436a2c4511f + # via sphinx +urllib3==2.2.2 \ + --hash=sha256:a448b2f64d686155468037e1ace9f2d2199776e17f0a46610480d311f73e3472 \ + --hash=sha256:dd505485549a7a552833da5e6063639d0d177c04f23bc3864e41e5dc5f612168 + # via requests diff --git a/tools/cr_checker/BUILD b/tools/cr_checker/BUILD new file mode 100644 index 0000000..ac13f73 --- /dev/null +++ b/tools/cr_checker/BUILD @@ -0,0 +1,35 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +load("//tools/cr_checker:cr_checker.bzl", "check", "fix") + +check( + name = "copyright.check", + srcs = [ + "//:BUILD", + "//:MODULE.bazel", + "//:repo_directories", + ], + offset = 24, + visibility = ["//visibility:public"], +) + +fix( + name = "copyright.fix", + srcs = [ + "//:BUILD", + "//:MODULE.bazel", + "//:repo_directories", + ], + visibility = ["//visibility:public"], +) diff --git a/tools/cr_checker/cr_checker.bzl b/tools/cr_checker/cr_checker.bzl new file mode 100644 index 0000000..cdc1fb3 --- /dev/null +++ b/tools/cr_checker/cr_checker.bzl @@ -0,0 +1,132 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +"""Defines Bazel rules for running copyright checks and fixes.""" + +load("@bazel_skylib//lib:paths.bzl", "paths") + +def _cr_impl(ctx): + """ + Implementation function for the copyright rule. This function sets up the + necessary command to execute the Python script with the specified mode and source files. + Args: + ctx (RuleContext): The rule context containing attributes and configuration. + Returns: + DefaultInfo: Bazel default information provider with the output log file. + """ + script = ctx.attr._script + files = [] + + files = ctx.files.srcs + extensions = ctx.attr.extensions + + text_exts = "" + if len(extensions): + text_exts = "-e {exts}".format( + exts = " ".join([exts for exts in ctx.attr.extensions]), + ) + + ctx.actions.write( + output = ctx.outputs.executable, + content = "{tool}.py -t {template} {extensions} {fix} {use_mmap} {debug} {log_file} {offset} {srcs}".format( + tool = script.files_to_run.executable.short_path, + template = ctx.file.template.path, + extensions = text_exts, + fix = "--fix" if ctx.attr.fix else "", + debug = "--verbose" if ctx.attr.debug else "", + use_mmap = "--use_memory_map" if ctx.attr.use_memory_map else "", + log_file = "--log-file log.txt" if ctx.attr.log_file else "", + offset = "--offset %s" % ctx.attr.offset if ctx.attr.offset else "", + srcs = " ".join([f.path for f in files]), + ), + ) + + runfiles = ctx.runfiles( + files = files + [ctx.file.template], + ).merge( + script.default_runfiles, + ) + return [DefaultInfo(runfiles = runfiles)] + +_cr_rule = rule( + implementation = _cr_impl, + executable = True, + attrs = { + "srcs": attr.label_list(allow_files = True, mandatory = False, default = []), + "template": attr.label(allow_single_file = True), + "extensions": attr.string_list(mandatory = False, default = []), + "debug": attr.bool(mandatory = False, default = False), + "fix": attr.bool(mandatory = False, default = False), + "offset": attr.int(mandatory = False, default = 0), + "log_file": attr.bool(mandatory = False, default = False), + "use_memory_map": attr.bool(mandatory = False, default = False), + "_script": attr.label( + default = Label("//tools/cr_checker/tool:cr_checker"), + ), + }, +) + +def check( + name, + srcs, + visibility, + template = "//tools/cr_checker/resources:templates", + extensions = [], + offset = 0, + debug = False, + log_file = False, + use_memory_map = False): + """ + Defines a Bazel target for checking files without modifying them. + Args: + name (str): The name of the target. + srcs (list of labels): The source files to check. + """ + _cr_rule( + name = name, + srcs = srcs, + template = template, + offset = offset, + debug = debug, + log_file = log_file, + use_memory_map = use_memory_map, + visibility = visibility, + ) + +def fix( + name, + srcs, + visibility, + template = "//tools/cr_checker/resources:templates", + extensions = [], + offset = 0, + debug = False, + log_file = False, + use_memory_map = False): + """ + Defines a Bazel target for fixing files by adding missing copyright text. + Args: + name (str): The name of the target. + srcs (list of labels): The source files to fix. + """ + _cr_rule( + name = name, + srcs = srcs, + template = template, + offset = offset, + debug = debug, + log_file = log_file, + use_memory_map = use_memory_map, + fix = True, + visibility = visibility, + ) diff --git a/tools/cr_checker/resources/BUILD b/tools/cr_checker/resources/BUILD new file mode 100644 index 0000000..b4b9ed7 --- /dev/null +++ b/tools/cr_checker/resources/BUILD @@ -0,0 +1,20 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +filegroup( + name = "templates", + srcs = [ + "templates.ini", + ], + visibility = ["//visibility:public"], +) diff --git a/tools/cr_checker/resources/templates.ini b/tools/cr_checker/resources/templates.ini new file mode 100644 index 0000000..fc0a711 --- /dev/null +++ b/tools/cr_checker/resources/templates.ini @@ -0,0 +1,56 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +[cpp,c,h,hpp] +/******************************************************************************** +* Copyright (c) 2024 Contributors to the Eclipse Foundation +* +* See the NOTICE file(s) distributed with this work for additional +* information regarding copyright ownership. +* +* This program and the accompanying materials are made available under the +* terms of the Apache License Version 2.0 which is available at +* https://www.apache.org/licenses/LICENSE-2.0 +* +* SPDX-License-Identifier: Apache-2.0 +********************************************************************************/ + +[py,sh,bzl,ini,BUILD] +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +[rst] +.. + # ******************************************************************************* + # Copyright (c) 2024 Contributors to the Eclipse Foundation + # + # See the NOTICE file(s) distributed with this work for additional + # information regarding copyright ownership. + # + # This program and the accompanying materials are made available under the + # terms of the Apache License Version 2.0 which is available at + # https://www.apache.org/licenses/LICENSE-2.0 + # + # SPDX-License-Identifier: Apache-2.0 + # ******************************************************************************* + diff --git a/tools/cr_checker/tool/BUILD b/tools/cr_checker/tool/BUILD new file mode 100644 index 0000000..39ef814 --- /dev/null +++ b/tools/cr_checker/tool/BUILD @@ -0,0 +1,20 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +py_binary( + name = "cr_checker", + srcs = [ + "cr_checker.py", + ], + visibility = ["//visibility:public"], +) diff --git a/tools/cr_checker/tool/README.md b/tools/cr_checker/tool/README.md new file mode 100644 index 0000000..6c7ee01 --- /dev/null +++ b/tools/cr_checker/tool/README.md @@ -0,0 +1,83 @@ +# CopyRight Checker + +`cr_checker.py` is a tool designed to check if files contain a specified copyright header. It provides configurable logging, color-coded console output, and can handle large file sets efficiently. The script supports reading configuration files for custom copyright templates and can utilize memory-mapped file reading for better performance with large files. Tool itself can also appened copyright header at the beggining of file if flag `--fix` is used. + +## Features + +- Checks files for specified copyright headers based on file extensions. +- Configurable logging, including color-coded output for easy visibility of log levels. +- Supports parameter files for flexible input handling. +- Can use memory mapping for large file handling. +- Customizable file encoding and offset adjustments for header text positioning. +- Can append copyright headers. + +## Requirements + +- Python 3.6+ +- `argparse`, `logging`, `os`, `sys`, `mmap`, `tempfile`, and `pathlib` (standard library modules) + +## Installation + +To use `cr_checker.py`, simply clone this repository. + +## Usage + +The script can be run from the command line with various options to customize its behavior: + +```bash +python cr_checker.py -t [options] +``` + +### Arguments + +- **-t**, **--template-file**: (Required) Path to the template file that defines the copyright text for each file extension. +- **-v**, **--verbose**: Enable debug-level logging. +- **-l**, **--log-file**: Path to a log file where logs will be saved. If not provided, logs will print to the console. +- **-e**, **--extensions**: List of file extensions to filter, e.g., -e .py .cpp. +- **--use_memory_map**: Use memory-mapped file reading for large files. +- **--encoding**: File encoding (default is utf-8). +- **--offset**: Additional offset for the header length to account for lines like a shebang. +- **--fix**: Setting script into fix mode where copyright header will be added to the files if it's missing from same. +- **inputs**: (Required) Directories or files to parse, or a parameter file prefixed with @ that lists files or directories. + +### Examples + +```sh +python cr_checker.py -t templates.ini -e py cpp -v -l logs.txt my_random_file.cpp my_random_file.py + +python cr_checker.py -t templates.ini -e py cpp --offset 24 --use_memory_map @files_to_check.txt + +python cr_checker.py -t templates.ini -e py cpp --fix --offset 24 --use_memory_map @files_to_check.txt + +``` + +### Template File Format + +The template file should be in INI format, with each section representing a file extension and a template key specifying the copyright text. + +Example templates.ini: + +```ini +[py,sh] +template = # Copyright (c) 2024 Score Project + +[cpp,c,hpp, h] +template = // Copyright (c) 2024 Score Project +``` + +## Exit Codes + +- 0: All files contain the required copyright text. +- 1: Some files are missing the required copyright text. +- Other: Error encountered during file processing. + +### Logging and Color-Coded Output + +By default, logs are printed to the console in color-coded format to indicate log levels. You can redirect logs to a file using the -l option. + +#### Log Colors + +- DEBUG: Blue +- INFO: Green +- WARNING: Yellow +- ERROR: Red diff --git a/tools/cr_checker/tool/cr_checker.py b/tools/cr_checker/tool/cr_checker.py new file mode 100755 index 0000000..be3a380 --- /dev/null +++ b/tools/cr_checker/tool/cr_checker.py @@ -0,0 +1,555 @@ +#!/usr/bin/env python3 + +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +"""The tool for checking if artifacts have proper copyright.""" + +import argparse +import os +import logging +import sys +import tempfile +import mmap +from pathlib import Path + +LOGGER = logging.getLogger() + +COLORS = { + "BLUE": "\033[34m", + "GREEN": "\033[32m", + "YELLOW": "\033[33m", + "RED": "\033[31m", + "DARK_RED": "\033[35;1m", + "ENDC": "\033[0m", +} + +LOGGER_COLORS = { + "DEBUG": COLORS["BLUE"], + "INFO": COLORS["GREEN"], + "WARNING": COLORS["YELLOW"], + "ERROR": COLORS["RED"], + "CRITICAL": COLORS["DARK_RED"], +} + + +class ColoredFormatter(logging.Formatter): + """ + A custom logging formatter to add color to log level names based on the logging level. + + The `ColoredFormatter` class extends `logging.Formatter` and overrides the `format` + method to add color codes to the log level name (e.g., `INFO`, `WARNING`, `ERROR`) + based on a predefined color mapping in `LOGGER_COLORS`. This color coding helps in + visually distinguishing log messages by severity. + + Attributes: + LOGGER_COLORS (dict): A dictionary mapping log level names (e.g., "INFO", "ERROR") + to their respective color codes. + COLORS (dict): A dictionary of terminal color codes, including an "ENDC" key to reset + colors after the level name. + + Methods: + format(record): Adds color to the `levelname` attribute of the log record and then + formats the record as per the superclass `Formatter`. + """ + + def format(self, record): + log_color = LOGGER_COLORS.get(record.levelname, "") + record.levelname = f"{log_color}{record.levelname}:{COLORS['ENDC']}" + return super().format(record) + + +class ParamFileAction(argparse.Action): # pylint: disable=too-few-public-methods + """ + A custom argparse action to support exclusive parameter files for command-line arguments. + + The `ParamFileAction` class allows users to specify a parameter file (prefixed with '@') + containing file paths or other inputs, which will override any additional inputs provided + in the command line. If a parameter file is found, its contents are used exclusively, + and all other inputs are ignored. If no parameter file is provided, standard inputs are used. + + Attributes: + parser (argparse.ArgumentParser): The argument parser instance. + namespace (argparse.Namespace): The namespace where arguments are stored. + values (list): The list of argument values passed from the command line. + option_string (str, optional): The option string that triggered this action, if any. + + Methods: + __call__(parser, namespace, values, option_string=None): Processes the arguments. + - If any value starts with '@', it reads the parameter file and sets `file_paths` + in `namespace`. + - If no parameter file is detected, it directly assigns `values` to `namespace`. + """ + + def __call__(self, parser, namespace, values, option_string=None): + paramfile = next((v[1:] for v in values if v.startswith("@")), None) + if paramfile: + with open(paramfile, "r", encoding="utf-8") as handle: + file_paths = [line.strip() for line in handle if line.strip()] + setattr(namespace, self.dest, file_paths) + else: + setattr(namespace, self.dest, values) + + +def load_templates(path): + """ + Loads the copyright templates from a configuration file. + + Args: + path (str): Path to the template file. + + Returns: + dict: A dictionary where each key is a file extension (e.g., ".cpp") + and the value is the template string from the config. + """ + templates = {} + current_extensions = [] + + with open(path, "r", encoding="utf-8") as file: + lines = file.readlines() + templates_for_extensions = "" + + for line in lines: + stripped_line = line.strip() + + if stripped_line.startswith("[") and stripped_line.endswith("]"): + if current_extensions: + for ext in current_extensions: + templates[ext] = templates_for_extensions + templates_for_extensions = "" + current_extensions = [] + + extensions = stripped_line[1:-1].split(",") + current_extensions = [ext.strip() for ext in extensions] + LOGGER.debug(current_extensions) + elif current_extensions: + templates_for_extensions += line + + if line.strip() == "": + for ext in current_extensions: + templates[ext] = templates_for_extensions + templates_for_extensions = "" + current_extensions = [] + + if current_extensions: + for ext in current_extensions: + templates[ext] = templates_for_extensions + + LOGGER.debug(templates) + return templates + + +def configure_logging(log_file_path=None, verbose=False): + """ + Configures logging to write messages to the specified log file. + + Args: + log_file_path (str, optional): Path to the log file. + verbose (bool, optional): If True, sets log level to DEBUG. Otherwise, sets it to INFO. + """ + log_level = logging.DEBUG if verbose else logging.INFO + LOGGER.setLevel(log_level) + LOGGER.handlers.clear() + + if log_file_path is not None: + handler = logging.FileHandler(log_file_path) + formatter = logging.Formatter("%(levelname)s: %(message)s") + else: + handler = logging.StreamHandler() + formatter = ColoredFormatter("%(levelname)s %(message)s") + + handler.setLevel(log_level) + handler.setFormatter(formatter) + LOGGER.addHandler(handler) + + +def load_text_from_file(path, header_length, encoding, offset): + """ + Reads the first portion of a file, up to `header_length` characters + plus an additional offset if provided. + + Args: + path (Path): A `pathlib.Path` object pointing to the file. + header_length (int): Number of characters to read for the header. + encoding (str): Encoding type to use when reading the file. + offset (int): Additional number of characters to read beyond + `header_length`, typically used to account for extra + lines (such as a shebang) before the header. + + Returns: + str: The portion of the file read, which should contain the header if present, + including any extra characters specified by `offset`. + """ + total_length = header_length + offset + LOGGER.debug( + "Reading first %d characters from file: %s [%s]", total_length, path, encoding + ) + with open(path, "r", encoding=encoding) as handle: + return handle.read(total_length) + + +def load_text_from_file_with_mmap(path, header_length, encoding, offset): + """ + Maps the file and reads only the first `header_length` bytes plus + an additional offset if provided. + + Args: + path (Path): A `pathlib.Path` object pointing to the file. + header_length (int): Length of the header text to check. + encoding (str): String for setting decoding type. + offset (int): Additional number of characters to read beyond + `header_length`, typically used to account for extra + lines (such as a shebang) before the header. + + Returns: + str: The portion of the file read, which should contain the header if present. + """ + + file_size = os.path.getsize(path) + total_length = header_length + offset + length = min(total_length, file_size) + + if not length: + LOGGER.warning( + "File %s is empty [length: %d]. Return empty string.", path, length + ) + return "" + + LOGGER.debug("Memory mapping first %d bytes from file: %s", header_length, path) + with open(path, "r", encoding=encoding) as handle: + with mmap.mmap(handle.fileno(), length=length, access=mmap.ACCESS_READ) as fmap: + return fmap[:header_length].decode(encoding) + + +def has_copyright(path, copyright_text, use_mmap, encoding, offset): + """ + Checks if the specified copyright text is present in the beginning of a file. + + Args: + path (Path): A `pathlib.Path` object pointing to the file to check. + copyright_text (str): The copyright text to search for at the beginning + of the file. + use_mmap (bool): If True, uses memory-mapped file reading for efficient + large file handling. + encoding (str): Encoding type to use when reading the file. + offset (int): Additional number of characters to read beyond the length + of `copyright_text`, used to account for extra content + (such as a shebang) before the copyright text. + + Returns: + bool: True if the file contains the copyright text, False if it is missing. + + Raises: + IOError: If there is an error opening or reading the file. + """ + + load_text = load_text_from_file + if use_mmap: + load_text = load_text_from_file_with_mmap + + if copyright_text not in load_text(path, len(copyright_text), encoding, offset): + return False + LOGGER.debug("File %s has copyright.", path) + return True + + +def get_files_from_dir(directory, exts=None): + """ + Finds files in the specified directories. Filters by extensions if provided. + + Args: + dirs (list of str): List of directories to search for files. + exts (list of str, optional): List of extensions to filter files. + If None, all files are returned. + + Returns: + list of str: List of file paths found in the directories. + """ + collected_files = [] + LOGGER.debug("Getting files from directory: %s", directory) + for path in directory.rglob("*"): + if path.is_file(): + if exts is None or path.suffix[1:] in exts: + collected_files.append(path) + return collected_files + + +def collect_inputs(inputs, exts=None): + """ + Collects files from a list of input paths, optionally filtering by file extensions. + + Args: + inputs (list): A list of paths to files or directories. + If a directory is provided, all files within it are added to the output. + exts (list, optional): A list of file extensions to filter by (e.g., ['.py', '.txt']). + Only files with these extensions will be included if specified. + + Returns: + list: A list of file paths collected from the input paths, filtered by the given extensions. + If an input is neither a file nor a directory, it is skipped with a warning. + + Logs: + Logs messages at the DEBUG level, detailing processing of directories and files, + and warns if an invalid input path is encountered. + """ + all_files = [] + LOGGER.debug("Extensions: %s", exts) + for i in inputs: + item = Path(i) + if item.is_dir(): + LOGGER.debug("Processing directory: %s", item) + all_files.extend(get_files_from_dir(item, exts)) + elif item.is_file() and (exts is None or item.suffix[1:] in exts): + LOGGER.debug("Processing file: %s", item) + all_files.append(item) + else: + LOGGER.warning("Skipped (input is not a valid file or directory): %s", item) + return all_files + + +def create_temp_file(path, encoding): + """ + Creates a temporary file with the provided content. + + Args: + path (str): The path of file to write the content to the temporary file. + encoding (str, optional): Encoding type to use when writing the file. + + Returns: + str: The path to the temporary file created. + """ + with tempfile.NamedTemporaryFile(mode="w", encoding=encoding, delete=False) as temp: + with open(path, "r", encoding=encoding) as handle: + for chunk in iter(lambda: handle.read(4096), ""): + temp.write(chunk) + return temp.name + + +def fix_copyright(path, copyright_text, encoding, offset): + """ + Inserts a copyright header into the specified file, ensuring that existing + content is preserved according to the provided offset. + + Args: + path (str): The path to the file that needs the copyright header. + copyright_text (str): The copyright text to be added. + encoding (str): The character encoding used to read and write the file. + offset (int): The number of bytes to preserve at the top of the file. + If 0, the first line is overwritten unless it's empty. + For non-zero offsets, ensures the correct number of bytes + are preserved. + """ + + temporary_file = create_temp_file(path, encoding) + + with open(temporary_file, "r", encoding=encoding) as temp: + # Read the first bytes of first line to check if it is equal to the offset + first_line = temp.readline() + byte_array = len(first_line.encode(encoding)) + + if offset > 0 and offset != byte_array: + LOGGER.error("Invalid offset value: %d, expected: %d", offset, byte_array) + return + + with open(path, "w", encoding=encoding) as handle: + if offset > 0: + handle.write(first_line + "\n") + handle.write(copyright_text) + # Reset the file pointer to the beginning of the temporary file + temp.seek(0) + for chunk in iter(lambda: temp.read(4096), ""): + handle.write(chunk) + LOGGER.info("Fixed missing header in: %s", path) + + +def process_files(files, templates, fix, use_mmap=False, encoding="utf-8", offset=0): # pylint: disable=too-many-arguments + """ + Processes a list of files to check for the presence of copyright text. + + Args: + files (list): A list of file paths to check. + templates (dict): A dictionary where keys are file extensions + (e.g., '.py', '.txt') and values are strings or patterns + representing the required copyright text. + use_mmap (bool): Flag for using mmap function for reading files + (instead of standard option). + encoding (str): Encoding type to use when reading the file. + offset (int): Additional number of characters to read beyond the length + of `copyright_text`, used to account for extra content + (such as a shebang) before the copyright text. + + Returns: + int: The number of files that do not contain the required copyright text. + """ + results = {"no_copyright": 0, "fixed": 0} + for item in files: + name = Path(item).name + key = name if name == "BUILD" else Path(item).suffix[1:] + if key not in templates.keys(): + logging.debug( + "Skipped (no configuration for selected file extension): %s", item + ) + continue + if not has_copyright(item, templates[key], use_mmap, encoding, offset): + if fix: + fix_copyright(item, templates[key], encoding, offset) + results["no_copyright"] += 1 + results["fixed"] += 1 + else: + LOGGER.error( + "Missing copyright header in: %s, use --fix to introduce it", item + ) + results["no_copyright"] += 1 + return results + + +def parse_arguments(argv): + """ + Parses command-line arguments. + + Args: + argv (list of str): List of command-line arguments. + + Returns: + argparse.Namespace: Parsed arguments containing files, directories, + copyright_file, extensions and log_file. + """ + parser = argparse.ArgumentParser( + description="A script to check for copyright in files with specific extensions." + ) + + parser.add_argument( + "-t", + "--template-file", + type=Path, + required=True, + help="Path to the template file", + ) + + parser.add_argument( + "-v", "--verbose", action="store_true", help="Enable debug logging level" + ) + + parser.add_argument( + "-l", + "--log-file", + type=Path, + default=None, + help="Redirect logs from STDOUT to this file", + ) + + parser.add_argument( + "-e", + "--extensions", + type=str, + nargs="+", + default=None, + help="List of extensions to filter when searching for files, e.g., '.h .cpp'", + ) + + parser.add_argument( + "--use_memory_map", + action="store_true", + help="Use memory map for reading conent of files \ + (should be used reading gigabyte ranged files).", + ) + + parser.add_argument( + "-f", + "--fix", + action="store_true", + help="Fix missing copyright headers by inserting them", + ) + + parser.add_argument( + "--encoding", default="utf-8", help="File encoding (default: utf-8)." + ) + + parser.add_argument( + "--offset", + dest="offset", + type=int, + default=0, + help="Additional length offset to account for characters like a shebang (default is 0)", + ) + + parser.add_argument( + "inputs", + nargs="+", + action=ParamFileAction, + help="Directories and/or files to parse.", + ) + + return parser.parse_args(argv) + + +def main(argv=None): + """ + Entry point for processing files to check for the presence of required copyright text. + + This function parses command-line arguments, configures logging, loads copyright templates, + collects input files based on provided criteria, and checks each file for the required + copyright text. + + Args: + argv (list, optional): List of command-line arguments. + If `None`, defaults to `sys.argv[1:]`. + + Returns: + int: Error code if an IOError occurs during loading templates or collecting input files; + otherwise, returns 0 as success. + """ + args = parse_arguments(argv if argv is not None else sys.argv[1:]) + configure_logging(args.log_file, args.verbose) + + try: + templates = load_templates(args.template_file) + except IOError as err: + LOGGER.error("Failed to load copyright text: %s", err) + return err.errno + + try: + files = collect_inputs(args.inputs, args.extensions) + except IOError as err: + LOGGER.error("Failed to prcess file %s with error", err.filename) + return err.errno + + LOGGER.debug("Running check on files: %s", files) + + results = process_files( + files, templates, args.fix, args.use_memory_map, args.encoding, args.offset + ) + total_no = results["no_copyright"] + total_fixes = results["fixed"] + + LOGGER.info("=" * 64) + LOGGER.info("Process completed.") + LOGGER.info( + "Total files without copyright: %s%d%s", + COLORS["GREEN"], + total_no, + COLORS["ENDC"], + ) + LOGGER.info( + "Total files that were fixed: %s%d%s", + COLORS["RED"] if total_fixes > 0 else COLORS["GREEN"], + total_fixes, + COLORS["ENDC"], + ) + LOGGER.info("=" * 64) + + return 0 if total_no == 0 else 1 + + +if __name__ == "__main__": + sys.exit(main(sys.argv[1:])) diff --git a/tools/format/BUILD b/tools/format/BUILD new file mode 100644 index 0000000..3bf7c6d --- /dev/null +++ b/tools/format/BUILD @@ -0,0 +1,36 @@ +# ******************************************************************************* +# Copyright (c) 2024 Contributors to the Eclipse Foundation +# +# See the NOTICE file(s) distributed with this work for additional +# information regarding copyright ownership. +# +# This program and the accompanying materials are made available under the +# terms of the Apache License Version 2.0 which is available at +# https://www.apache.org/licenses/LICENSE-2.0 +# +# SPDX-License-Identifier: Apache-2.0 +# ******************************************************************************* + +load("@aspect_rules_lint//format:defs.bzl", "format_multirun", "format_test") + +format_multirun( + name = "format.fix", + python = "@aspect_rules_lint//format:ruff", + starlark = "@buildifier_prebuilt//:buildifier", + visibility = [ + "//visibility:public", + ], + yaml = "@aspect_rules_lint//format:yamlfmt", +) + +format_test( + name = "format.check", + no_sandbox = True, + python = "@aspect_rules_lint//format:ruff", + starlark = "@buildifier_prebuilt//:buildifier", + visibility = [ + "//visibility:public", + ], + workspace = "//:MODULE.bazel", + yaml = "@aspect_rules_lint//format:yamlfmt", +)