开源不是「代码公开了就可以随便用」——每个仓库都有许可证,每个许可证都有一组权利和义务。cann-agreements 是 CANN 社区的许可证管理仓库:明确每个仓库使用的许可证、第三方依赖的许可证合规性、以及贡献代码时的 CLA(Contributor License Agreement)签署流程。

CANN 仓库的许可证结构

CANN 的 55 个仓库并不共用一个许可证——不同类型的仓库使用不同的许可证:

许可证类型分布

Apache 2.0(允许商用/修改/分发/专利授权,最宽松)
  → 算子仓库(ops-*)、加速库(catlass/ATB 等)、学习资源
  → 覆盖 40+ 个仓库,是 CANN 的主许可证

MIT(极简许可证,仅要求保留版权声明)
  → 工具类小仓库(cmake 辅助脚本、CI 配置片段)
  → 覆盖 < 5 个仓库

木兰宽松许可证 v2(国内开源许可证,兼容多种许可证)
  → 部分社区治理仓库(community、release-management)
  → 覆盖 3-5 个仓库

自定义许可证(华为内部/特殊场景)
  → 涉及固件/驱动/硬件文档的仓库
  → 覆盖 driver、metadef 等编译运行类仓库

许可证的选择影响:企业能否商用、是否必须开源修改的代码、是否需要保留版权声明。

Apache 2.0 的核心条款

算子仓库都用 Apache 2.0——这是业界最宽松的许可证之一:

Apache 2.0 的四大权利
├─ 商用:可以在商业产品中使用,不需要付费
├─ 修改:可以修改代码,不需要通知任何人
├─ 分发:可以把代码打包成产品/库分发
└─ 专利授权:自动授予所有用户使用相关专利的权利

Apache 2.0 的两项义务
├─ 保留版权声明:所有源文件头部保留原始版权声明和 Apache 声明
└─ 声明重大变更:修改后的文件要标注 "Licensed under the Apache License, Version 2.0"

实战场景:一家公司从 ops-nn 拿了 GEMM 优化代码,改了内部的 tiling 参数,装进自己的推理引擎卖给了客户。完全合规——不需要开源,不需要付费,不需要告知昇腾。

第三方依赖的许可证合规

算子仓库不可避免地依赖第三方库——FFT 仓库可能引用 FFTW(GNU GPL),ML 仓库可能引用某些 CC 协议库。cann-agreements 定义了依赖许可证的审核流程:

依赖许可证审核流程

Step 1:发现依赖
  ├── 显式依赖:package.json / requirements.txt / CMakeLists.txt
  └── 间接依赖:依赖的依赖(transitive dependencies)

Step 2:分类许可证风险
  ├── 高风险(需替换或隔离)
  │   ├── GPL / AGPL:传染性强,使用者必须开源
  │   ├── SSPL:MongoDB 许可证,禁止直接 SaaS 使用
  │   └── Custom/Proprietary:需要商业谈判
  │
  ├── 中风险(需要确认兼容性)
  │   ├── LGPL:动态链接可接受,静态链接需要特殊处理
  │   ├── MPL:文件级许可证,允许部分开源
  │   └── CC-BY-NC:非商业用途限制
  │
  └── 低风险(直接可用)
      ├── Apache 2.0 / MIT / BSD / ISC:直接使用
      └── 木兰宽松许可证 v2:国内场景优先选

贡献者的 CLA 签署

在 CANN 社区提交 PR 之前,需要签署 CLA(Contributor License Agreement)。CLA 的核心作用是:贡献者授权华为将代码合入 CANN 仓库,并确保贡献的代码没有侵犯第三方知识产权。

# 签署 CLA 的流程
# 1. 在 AtomGit 上打开 PR,CLA 机器人会自动检测
# 2. 首次贡献需要先签署 CLA

# CLA 签署页面
# https://atomgit.com/cann/cann-agreements/blob/main/CLA.md

# 签署 CLA 的关键步骤:

# Step 1:确认你是个人贡献者还是代表公司
# - 个人贡献:签署 IC-LA(个人贡献者协议)
# - 公司贡献:需要公司签署 CCL(Corporate CLA),个人签署 IC-LA

# Step 2:阅读 CLA 内容,确认以下条款
# - 贡献的代码归贡献者所有(有权贡献)
# - 没有剽窃第三方代码(如 GPL 代码未经许可的片段)
# - 授予华为 在 CANN 仓库中 使用/修改/分发 该代码的权利
# - 如果代码涉及专利,授予所有用户 免版权费 的专利使用权

# Step 3:签署(电子签名)
# 在 PR 评论里回复 "+CLA Signed"

# 4. CLA Bot 检查通过,PR 可以继续审查
# 如果 CLA 签署状态有变化,Bot 会在 PR 下发评论

许可证兼容性的判定矩阵

当一个项目依赖多个许可证的组件时,需要判断最终产品的许可证。最常见的场景:

组件 A 组件 B 组合后许可证 说明
Apache 2.0 Apache 2.0 Apache 2.0 兼容
Apache 2.0 MIT Apache 2.0 兼容(MIT 被 Apache 2.0 覆盖)
Apache 2.0 BSD-2 Apache 2.0 兼容
Apache 2.0 BSD-3 Apache 2.0 兼容
Apache 2.0 GPL-3.0 冲突 GPL 传染性导致整体成为 GPL
Apache 2.0 LGPL-2.1 动态链接:Apache 2.0;静态链接:GPL 动态链接隔离
Apache 2.0 MPL-2.0 动态链接:Apache 2.0;静态链接:需额外审查 文件级许可

踩坑一:静态链接导致许可证传染

一个仓库用了 GPL-licensed 的库(ops-fft 引用了 GPL 的 FFT 实现),直接把库编译进自己的二进制——这个仓库的许可证就从 Apache 2.0 变成了 GPL。

# 错误:直接把 GPL 库静态链接到 ops-fft
# CMakeLists.txt
target_link_libraries(ops-fft PUBLIC gpl_fft_lib)  # ← 传染!

# 正确做法:用动态链接( LGPL 下的动态链接可接受)
target_link_libraries(ops-fft PUBLIC gpl_fft_lib_shared)  # 动态 .so 文件
# 或者替换成 Apache 2.0 的 FFT 实现(如 kissfft)
target_link_libraries(ops-fft PUBLIC kissfft)  # MIT 许可证,无传染风险

踩坑二:COPYRIGHT 文件缺失导致的法律风险

Apache 2.0 要求保留所有源文件的版权声明。如果删掉了某个源文件头部的版权声明——即使保留了代码本身——也是违反许可证的行为。

自动化检查:在 CI 里加 reuse lint(EU 的 REUSE 规范)或 licensee(检查许可证合规性的工具)。

# 检查项目许可证合规性
licensee detect

# 输出示例:
# No license file found. Detecting license(s) in code...
# ...
# ✓ LICENSE file matches Apache-2.0
#
# Unused licenses:
#   - No SPDX expression in package.json (found: undefined)
#   - Some files missing copyright notices

# 未检测到的文件列表
# 需要手动补充 COPYRIGHT 文件或在每个源文件头部加版权声明

踩坑三:贡献代码时剽窃了第三方代码

提交的 PR 里有几行代码是从 Stack Overflow 或某个 GPL 项目复制来的。CLA 签署时声明「贡献的代码归贡献者所有」,但实际代码并非原创——CLA 条款不被满足,PR 合入后可能引发法律纠纷。

自动化检测:CLA Bot 会跑 cloc(代码行数统计)和 scancode-toolkit(许可证扫描)对比 PR 和公开代码库的重合度。

# 检测 PR 中代码和公开代码库的重合度
scancode-toolkit --license \
    --classify \
    --is-license-text \
    --output-file=scan_result.json \
    ./PR_changes/

# 关键指标:
# - clone_detector:和已知开源项目的代码行重合比例
# - snippet_matches:从 Stack Overflow 等来源的代码片段

# 如果 clone_detector > 30%:
# CLA Bot 会标记 PR 为「需要人工审查」
# 贡献者需要提供代码来源证明(原创/合理使用/已获授权)

踩坑四:多许可证项目的许可证头注释混乱

一个仓库同时包含 Apache 2.0(自研代码)和 MIT(第三方脚本)两个许可证——有的文件头部有版权声明,有的没有。时间久了维护者分不清哪个文件用哪个许可证。

统一格式:在仓库根目录放 NOTICE.md 列出所有第三方来源,在每个源文件头部统一 SPDX 标识。

// 统一格式:用 SPDX 标识许可证
// Copyright (C) 2025 Huawei Technologies Co., Ltd.
// SPDX-License-Identifier: Apache-2.0

// 第三方引入的脚本(COPYING 是 MIT 许可证的原文)
// Copyright (C) 2023 Original Author
// SPDX-License-Identifier: MIT

SPDX(Software Package Data Exchange)是 Linux 基金会主导的许可证标识标准——每个许可证的 SPDX Identifier 是唯一的:Apache-2.0MITGPL-3.0-only 等等。编译器能识别 SPDX 注释,CI 能自动检查许可证合规性。


开源合规不是法务的事,是工程师的事。每个仓库用什么许可证、依赖的库是什么许可证、贡献的代码有没有侵权风险——这些在写代码的时候就要搞清楚,而不是等 PR 合入之后才发现许可证冲突。cann-agrereements 把这些规则整理成可操作的手册,降低了贡献者踩坑的概率。

Logo

作为“人工智能6S店”的官方数字引擎,为AI开发者与企业提供一个覆盖软硬件全栈、一站式门户。

更多推荐