blob: 69e7668a700da07845fe9ed59a5b7474ec2e1c45 [file] [log] [blame]
# Copyright (c) 2020-2021 Project CHIP Authors
#
# 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.
name: Lint Code Base
on:
push:
pull_request:
merge_group:
workflow_dispatch:
concurrency:
group: ${{ github.ref }}-${{ github.workflow }}-${{ (github.event_name == 'pull_request' && github.event.number) || (github.event_name == 'workflow_dispatch' && github.run_number) || github.sha }}
cancel-in-progress: true
jobs:
code-lints:
runs-on: ubuntu-latest
if: github.actor != 'restyled-io[bot]'
container:
image: ghcr.io/project-chip/chip-build:41
steps:
- name: Checkout
uses: actions/checkout@v4
# Bootstrap and checkout for internal scripts (like idl_lint)
# to run
- name: Checkout submodules & Bootstrap
uses: ./.github/actions/checkout-submodules-and-bootstrap
with:
platform: linux
- name: Check for orphaned gn files
if: always()
# We should enforce that ALL new files are referenced in our build scripts.
# Several things do not have a clear fix path:
# - various platform implementations (including darwin-specific files as they
# are not using GN)
# - app/clusters (they are fetched dynamically - this should probably be fixed)
#
# All the rest of the exceptions should be driven down to 0: chip should fully
# be defined in build rules.
#
# This check enforces that for any newly added file, it must be part of some
# BUILD.gn file
run: |
./scripts/run_in_build_env.sh "./scripts/tools/not_known_to_gn.py \
src \
--skip-dir app/clusters \
--skip-dir darwin \
--skip-dir include \
--skip-dir platform/Ameba \
--skip-dir platform/android \
--skip-dir platform/ASR \
--skip-dir platform/Beken \
--skip-dir platform/bouffalolab \
--skip-dir platform/cc13xx_26xx \
--skip-dir platform/cc32xx \
--skip-dir platform/Darwin \
--skip-dir platform/ESP32 \
--skip-dir platform/fake \
--skip-dir platform/FreeRTOS \
--skip-dir platform/Infineon \
--skip-dir platform/Linux \
--skip-dir platform/mbed \
--skip-dir platform/mt793x \
--skip-dir platform/nxp \
--skip-dir platform/OpenThread \
--skip-dir platform/qpg \
--skip-dir platform/silabs \
--skip-dir platform/telink \
--skip-dir platform/webos \
--skip-dir platform/Zephyr \
--skip-dir test_driver \
--known-failure app/app-platform/ContentApp.cpp \
--known-failure app/app-platform/ContentApp.h \
--known-failure app/app-platform/ContentAppPlatform.cpp \
--known-failure app/app-platform/ContentAppPlatform.h \
--known-failure controller/ExamplePersistentStorage.cpp \
--known-failure controller/ExamplePersistentStorage.h \
--known-failure app/AttributeAccessInterface.h \
--known-failure app/AttributeAccessToken.h \
--known-failure app/CommandHandler.h \
--known-failure app/CommandHandlerInterface.h \
--known-failure app/CommandSenderLegacyCallback.h \
--known-failure app/ReadHandler.h \
--known-failure app/reporting/reporting.cpp \
--known-failure app/reporting/tests/MockReportScheduler.cpp \
--known-failure app/reporting/tests/MockReportScheduler.h \
--known-failure app/TestEventTriggerDelegate.h \
--known-failure app/util/af.h \
--known-failure app/util/attribute-storage.cpp \
--known-failure app/util/attribute-storage.h \
--known-failure app/util/attribute-table.cpp \
--known-failure app/util/attribute-table.h \
--known-failure app/util/binding-table.cpp \
--known-failure app/util/binding-table.h \
--known-failure app/util/config.h \
--known-failure app/util/DataModelHandler.cpp \
--known-failure app/util/DataModelHandler.h \
--known-failure app/util/ember-compatibility-functions.cpp \
--known-failure app/util/ember-compatibility-functions.h \
--known-failure app/util/endpoint-config-api.h \
--known-failure app/util/generic-callbacks.h \
--known-failure app/util/generic-callback-stubs.cpp \
--known-failure app/util/im-client-callbacks.h \
--known-failure app/util/util.cpp \
--known-failure app/util/util.h \
--known-failure app/WriteHandler.h \
--known-failure platform/DeviceSafeQueue.cpp \
--known-failure platform/DeviceSafeQueue.h \
--known-failure platform/GLibTypeDeleter.h \
--known-failure platform/SingletonConfigurationManager.cpp \
"
- name: Check for matter lint errors
if: always()
run: |
for idl_file in $(find . -name '*.matter'); do
# TODO: all these conformance failures should be fixed
# Issues exist for most of them:
# https://github.com/project-chip/connectedhomeip/issues/19176
# https://github.com/project-chip/connectedhomeip/issues/19175
# https://github.com/project-chip/connectedhomeip/issues/19173
if [ "$idl_file" = './examples/log-source-app/log-source-common/log-source-app.matter' ]; then continue; fi
if [ "$idl_file" = './examples/placeholder/linux/apps/app1/config.matter' ]; then continue; fi
if [ "$idl_file" = './examples/placeholder/linux/apps/app2/config.matter' ]; then continue; fi
if [ "$idl_file" = './examples/thermostat/thermostat-common/thermostat.matter' ]; then continue; fi
if [ "$idl_file" = './examples/window-app/common/window-app.matter' ]; then continue; fi
# Test files are intentionally small and not spec-compilant, just parse-compliant
if [ "$idl_file" = "./scripts/py_matter_idl/matter_idl/tests/inputs/cluster_struct_attribute.matter" ]; then continue; fi
if [ "$idl_file" = "./scripts/py_matter_idl/matter_idl/tests/inputs/global_struct_attribute.matter" ]; then continue; fi
if [ "$idl_file" = "./scripts/py_matter_idl/matter_idl/tests/inputs/optional_argument.matter" ]; then continue; fi
if [ "$idl_file" = "./scripts/py_matter_idl/matter_idl/tests/inputs/several_clusters.matter" ]; then continue; fi
if [ "$idl_file" = "./scripts/py_matter_idl/matter_idl/tests/inputs/simple_attribute.matter" ]; then continue; fi
if [ "$idl_file" = "./scripts/py_matter_idl/matter_idl/tests/inputs/large_lighting_app.matter" ]; then continue; fi
if [ "$idl_file" = "./scripts/py_matter_idl/matter_idl/tests/inputs/large_all_clusters_app.matter" ]; then continue; fi
./scripts/run_in_build_env.sh "./scripts/idl_lint.py --log-level warn $idl_file" >/dev/null || exit 1
done
- name: Check broken links
# On-push disabled until the job can run fully green
# At that point the step should be enabled.
if: github.event_name == 'workflow_dispatch'
uses: gaurav-nelson/github-action-markdown-link-check@v1
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for incorrect error use in VerifyOrExit
if: always()
run: |
git grep -I -n "VerifyOrExit(.*, [A-Za-z]*_ERROR" -- './*' ':(exclude).github/workflows/lint.yml' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of PRI*8, which are not supported on some libcs.
if: always()
run: |
git grep -I -n "PRI.8" -- './*' ':(exclude).github/workflows/lint.yml' ':(exclude)third_party/lwip/repo/lwip/src/include/lwip/arch.h' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of PRI*16, which are not supported on some libcs.
if: always()
run: |
git grep -I -n "PRI.16" -- './*' ':(exclude).github/workflows/lint.yml' ':(exclude)third_party/lwip/repo/lwip/src/include/lwip/arch.h' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of PRI*64, which are not supported on some libcs.
if: always()
run: |
# TODO: MessageDefHelper should ideally not be excluded here.
# TODO: chip_im_initiatore should ideally not be excluded here.
# TODO: TLVDebug should ideally not be excluded here.
# TODO: protocol_decoder.cpp should ideally not be excluded here.
# TODO: PersistentStorageMacros.h should ideally not be excluded here.
git grep -I -n "PRI.64" -- './*' ':(exclude).github/workflows/lint.yml' ':(exclude)examples/chip-tool' ':(exclude)examples/tv-casting-app' ':(exclude)src/app/MessageDef/MessageDefHelper.cpp' ':(exclude)src/app/tests/integration/chip_im_initiator.cpp' ':(exclude)src/lib/core/TLVDebug.cpp' ':(exclude)src/lib/dnssd/tests/TestTxtFields.cpp' ':(exclude)src/lib/format/protocol_decoder.cpp' ':(exclude)src/lib/support/PersistentStorageMacros.h' ':(exclude)src/messaging/tests/echo/echo_requester.cpp' ':(exclude)src/platform/Linux' ':(exclude)src/platform/Ameba' ':(exclude)src/platform/ESP32' ':(exclude)src/platform/Darwin' ':(exclude)src/darwin' ':(exclude)src/platform/webos' ':(exclude)zzz_generated/chip-tool' ':(exclude)src/tools/chip-cert/Cmd_PrintCert.cpp' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of %zu, which are not supported on some libcs.
if: always()
run: |
git grep -I -n "%zu" -- './*' ':(exclude).github/workflows/lint.yml' && exit 1 || exit 0
# Comments like '{{! ... }}' should be used in zap files
- name: Do not allow TODO in generated files
if: always()
run: |
git grep -n 'TODO:' -- ./zzz_generated './*/zap-generated/*' && exit 1 || exit 0
- name: Check for disallowed include files
if: always()
run: scripts/tools/check_includes.sh
- name: Check for zcl.json and extension sync status
if: always()
run: scripts/tools/check_zcl_file_sync.py .
- name: Ensure all PICS are set for tests (to true or false)
if: always()
run: |
scripts/tools/check_test_pics.py src/app/tests/suites/certification/ci-pics-values src/app/tests/suites/certification/PICS.yaml
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of 0x%u and the like, which lead to misleading output.
if: always()
run: |
git grep -I -n '0x%[0-9l.-]*[^0-9lxX".-]' -- './*' ':(exclude).github/workflows/lint.yml' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of '"0x" PRIu*' and the like, which lead to misleading output.
if: always()
run: |
git grep -I -n '0x%[0-9-]*" *PRI[^xX]' -- './*' ':(exclude).github/workflows/lint.yml' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match.
- name: Check for use of NSLog instead of Matter logging in Matter framework
if: always()
run: |
git grep -n 'NSLog(' -- src/darwin/Framework/CHIP && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself, as well as excluding the files
# that implement the type-safe accessors
- name: Check for use of 'emberAfReadAttribute' instead of the type-safe getters
if: always()
run: |
git grep -I -n 'emberAfReadAttribute' -- './*' ':(exclude).github/workflows/lint.yml' ':(exclude)src/app/util/af.h' ':(exclude)zzz_generated/app-common/app-common/zap-generated/attributes/Accessors.cpp' ':(exclude)src/app/zap-templates/templates/app/attributes/Accessors-src.zapt' ':(exclude)src/app/util/attribute-table.cpp' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself, as well as excluding the files
# that implement the type-safe accessors, attribute writing from the wire, and some
# Pigweed RPC code that seems hard to update.
- name: Check for use of 'emberAfWriteAttribute' instead of the type-safe setters
if: always()
run: |
git grep -I -n 'emberAfWriteAttribute' -- './*' ':(exclude).github/workflows/lint.yml' ':(exclude)src/app/util/af.h' ':(exclude)zzz_generated/app-common/app-common/zap-generated/attributes/Accessors.cpp' ':(exclude)src/app/zap-templates/templates/app/attributes/Accessors-src.zapt' ':(exclude)src/app/util/attribute-table.cpp' ':(exclude)examples/common/pigweed/rpc_services/Attributes.h' ':(exclude)src/app/util/attribute-table.h' ':(exclude)src/app/util/ember-compatibility-functions.cpp' && exit 1 || exit 0
# Run ruff python linter
- name: Check for errors using ruff Python linter
if: always()
run: |
ruff check
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of "SuccessOrExit(CHIP_ERROR_*)", which should probably be "SuccessOrExit(err = CHIP_ERROR_*)"
if: always()
run: |
git grep -I -n 'SuccessOrExit(CHIP_ERROR' -- './*' ':(exclude).github/workflows/lint.yml' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match. And we want to exclude this file,
# to avoid our grep regexp matching itself.
- name: Check for use of "SuccessOrExit(something-without-assignment(", which should probably be "SuccessOrExit(err = something("
if: always()
run: |
git grep -I -n 'SuccessOrExit([^=)]*(' -- './*' ':(exclude).github/workflows/lint.yml' && exit 1 || exit 0
# git grep exits with 0 if it finds a match, but we want
# to fail (exit nonzero) on match.
- name: Check for use of "using namespace" outside of a class/function in headers.
if: always()
run: |
# Various platforms have `using namespace chip::Ble` in their BLEManager* headers; just exclude those for now.
#
# Exclude platform openiotsdk bits that do this in their persistent storage header.
#
# Also exclude examples (for now) and third_party, which have various instances of this.
#
# Ignore uses of `System::Clock::Literals`, because that's the only way to have things using _ms32 or whatnot
# in a header file.
git grep -I -n -e '^using namespace' --and --not -e 'System::Clock::Literals' -- './**/*.h' ':(exclude)src/platform/*/BLEManager*.h' ':(exclude)src/platform/openiotsdk/KVPsaPsStore.h' ':(exclude)./examples' ':(exclude)./third_party' && exit 1 || exit 0