Compare commits
124 Commits
v4.3.0
...
v3.5-branc
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ac9c9d2c8d | ||
|
|
f780ff8154 | ||
|
|
acfd2b279d | ||
|
|
636d73e67a | ||
|
|
0ea4e22c6a | ||
|
|
e267abdc5d | ||
|
|
3ddd2734a9 | ||
|
|
6b2e403a75 | ||
|
|
fcd271d0dc | ||
|
|
b5d53e922f | ||
|
|
aa96c4d3cb | ||
|
|
d32ad62356 | ||
|
|
1424b494cd | ||
|
|
48ba8b406e | ||
|
|
75f737a5cc | ||
|
|
316637f865 | ||
|
|
68b759a214 | ||
|
|
3366400449 | ||
|
|
a8ac372cee | ||
|
|
eb8acf9d37 | ||
|
|
c1298b7af0 | ||
|
|
c34def10af | ||
|
|
d54f5337e3 | ||
|
|
43c538e8cc | ||
|
|
207639a3fd | ||
|
|
c641a3e2d0 | ||
|
|
91a8ed6064 | ||
|
|
a0aef88ee2 | ||
|
|
96c278e008 | ||
|
|
dff8361d9a | ||
|
|
24b9511fa5 | ||
|
|
012e361818 | ||
|
|
399f06e287 | ||
|
|
ab6606312d | ||
|
|
0bc62cc4bc | ||
|
|
491acd95c1 | ||
|
|
4728630fe5 | ||
|
|
411c7eb494 | ||
|
|
fd1972be62 | ||
|
|
af85375f11 | ||
|
|
77df4454f8 | ||
|
|
4507175d61 | ||
|
|
d3f72d7072 | ||
|
|
76a15672e6 | ||
|
|
d47129f0f7 | ||
|
|
b3dc1ff89d | ||
|
|
0e0cd2a0d7 | ||
|
|
ee3fab469d | ||
|
|
927ab297ef | ||
|
|
e6f480fc89 | ||
|
|
d0d9125eec | ||
|
|
2c700c1b5e | ||
|
|
e486e6ce62 | ||
|
|
cf24d48c52 | ||
|
|
95b772f231 | ||
|
|
0de7085475 | ||
|
|
002392c646 | ||
|
|
e867618593 | ||
|
|
48e9a63446 | ||
|
|
bc7d3dcc25 | ||
|
|
62e3c7d871 | ||
|
|
bc69b8054b | ||
|
|
a6f82ce330 | ||
|
|
f5f896f5c9 | ||
|
|
325c922846 | ||
|
|
5b999233ef | ||
|
|
e231b667aa | ||
|
|
db5475da27 | ||
|
|
64e2ec47cb | ||
|
|
b7dae51454 | ||
|
|
e9f997e2a1 | ||
|
|
f91ebabb28 | ||
|
|
15ada1522f | ||
|
|
2d8508ba32 | ||
|
|
469b2051ab | ||
|
|
6e4539f924 | ||
|
|
60c661dfc8 | ||
|
|
edad58e168 | ||
|
|
8a911d6bdd | ||
|
|
014571b046 | ||
|
|
49f04fd840 | ||
|
|
456496efa6 | ||
|
|
7eb8be25e3 | ||
|
|
8415778a1a | ||
|
|
aff7cbe65e | ||
|
|
54c11a17f5 | ||
|
|
86517b3353 | ||
|
|
214b74e103 | ||
|
|
6b12e12312 | ||
|
|
5a11de06b6 | ||
|
|
086b5b96db | ||
|
|
abd9ecdd23 | ||
|
|
a14c841af4 | ||
|
|
b872bca7c1 | ||
|
|
d8165a3fea | ||
|
|
91bf1b4ed4 | ||
|
|
954bd84d36 | ||
|
|
f9f78b4415 | ||
|
|
94ab004c84 | ||
|
|
a000c24e64 | ||
|
|
da3858eaaf | ||
|
|
98f09e3442 | ||
|
|
c65b84d2aa | ||
|
|
6c80bf4811 | ||
|
|
6f207d4d06 | ||
|
|
79a538dad0 | ||
|
|
3b52bc7b85 | ||
|
|
a2bb849472 | ||
|
|
45c19a9917 | ||
|
|
7ff91648cd | ||
|
|
2560cea906 | ||
|
|
76b340d210 | ||
|
|
b110f80cc8 | ||
|
|
796b8c7f96 | ||
|
|
2d4916cf78 | ||
|
|
9eee5b3681 | ||
|
|
a802b34af6 | ||
|
|
933e579728 | ||
|
|
480c64d3a7 | ||
|
|
ebe1ef02d3 | ||
|
|
63a769afad | ||
|
|
ced26e2340 | ||
|
|
46cf4486fa | ||
|
|
3a67f3d906 |
17
.github/workflows/bsim-tests.yaml
vendored
17
.github/workflows/bsim-tests.yaml
vendored
@@ -28,12 +28,11 @@ concurrency:
|
||||
jobs:
|
||||
bsim-test:
|
||||
if: github.repository_owner == 'zephyrproject-rtos'
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
container:
|
||||
image: ghcr.io/zephyrproject-rtos/ci:v0.26.5
|
||||
image: ghcr.io/zephyrproject-rtos/ci-repo-cache:v0.26.5.20231213
|
||||
options: '--entrypoint /bin/bash'
|
||||
volumes:
|
||||
- /repo-cache/zephyrproject:/github/cache/zephyrproject
|
||||
env:
|
||||
ZEPHYR_TOOLCHAIN_VARIANT: zephyr
|
||||
ZEPHYR_SDK_INSTALL_DIR: /opt/toolchains/zephyr-sdk-0.16.3
|
||||
@@ -52,10 +51,16 @@ jobs:
|
||||
# GitHub comes up with a fundamental fix for this problem.
|
||||
git config --global --add safe.directory ${GITHUB_WORKSPACE}
|
||||
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: Clone cached Zephyr repository
|
||||
continue-on-error: true
|
||||
run: |
|
||||
git clone --shared /github/cache/zephyrproject/zephyr .
|
||||
git clone --shared /repo-cache/zephyrproject/zephyr .
|
||||
git remote set-url origin ${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}
|
||||
|
||||
- name: Checkout
|
||||
@@ -75,7 +80,7 @@ jobs:
|
||||
west init -l . || true
|
||||
west config manifest.group-filter -- +ci
|
||||
west config --global update.narrow true
|
||||
west update --path-cache /github/cache/zephyrproject 2>&1 1> west.update.log || west update --path-cache /github/cache/zephyrproject 2>&1 1> west.update.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /github/cache/zephyrproject)
|
||||
west update --path-cache /repo-cache/zephyrproject 2>&1 1> west.update.log || west update --path-cache /repo-cache/zephyrproject 2>&1 1> west.update.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /repo-cache/zephyrproject)
|
||||
west forall -c 'git reset --hard HEAD'
|
||||
|
||||
- name: Check common triggering files
|
||||
|
||||
55
.github/workflows/clang.yaml
vendored
55
.github/workflows/clang.yaml
vendored
@@ -9,18 +9,20 @@ concurrency:
|
||||
jobs:
|
||||
clang-build:
|
||||
if: github.repository_owner == 'zephyrproject-rtos'
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
container:
|
||||
image: ghcr.io/zephyrproject-rtos/ci:v0.26.5
|
||||
image: ghcr.io/zephyrproject-rtos/ci-repo-cache:v0.26.5.20231213
|
||||
options: '--entrypoint /bin/bash'
|
||||
volumes:
|
||||
- /repo-cache/zephyrproject:/github/cache/zephyrproject
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
platform: ["native_posix"]
|
||||
env:
|
||||
ZEPHYR_SDK_INSTALL_DIR: /opt/toolchains/zephyr-sdk-0.16.3
|
||||
CCACHE_DIR: /node-cache/ccache-zephyr
|
||||
CCACHE_REMOTE_STORAGE: "redis://cache-*.keydb-cache.svc.cluster.local|shards=1,2,3"
|
||||
CCACHE_REMOTE_ONLY: "true"
|
||||
LLVM_TOOLCHAIN_PATH: /usr/lib/llvm-16
|
||||
COMMIT_RANGE: ${{ github.event.pull_request.base.sha }}..${{ github.event.pull_request.head.sha }}
|
||||
BASE_REF: ${{ github.base_ref }}
|
||||
@@ -35,10 +37,16 @@ jobs:
|
||||
# GitHub comes up with a fundamental fix for this problem.
|
||||
git config --global --add safe.directory ${GITHUB_WORKSPACE}
|
||||
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: Clone cached Zephyr repository
|
||||
continue-on-error: true
|
||||
run: |
|
||||
git clone --shared /github/cache/zephyrproject/zephyr .
|
||||
git clone --shared /repo-cache/zephyrproject/zephyr .
|
||||
git remote set-url origin ${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}
|
||||
|
||||
- name: Checkout
|
||||
@@ -64,7 +72,7 @@ jobs:
|
||||
# So first retry to update, if that does not work, remove all modules
|
||||
# and start over. (Workaround until we implement more robust module
|
||||
# west caching).
|
||||
west update --path-cache /github/cache/zephyrproject 2>&1 1> west.log || west update --path-cache /github/cache/zephyrproject 2>&1 1> west2.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /github/cache/zephyrproject)
|
||||
west update --path-cache /repo-cache/zephyrproject 2>&1 1> west.log || west update --path-cache /repo-cache/zephyrproject 2>&1 1> west2.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /repo-cache/zephyrproject)
|
||||
|
||||
- name: Check Environment
|
||||
run: |
|
||||
@@ -73,31 +81,12 @@ jobs:
|
||||
gcc --version
|
||||
ls -la
|
||||
|
||||
- name: Prepare ccache timestamp/data
|
||||
id: ccache_cache_timestamp
|
||||
shell: cmake -P {0}
|
||||
- name: Set up ccache
|
||||
run: |
|
||||
string(TIMESTAMP current_date "%Y-%m-%d-%H;%M;%S" UTC)
|
||||
string(REPLACE "/" "_" repo ${{github.repository}})
|
||||
string(REPLACE "-" "_" repo2 ${repo})
|
||||
file(APPEND $ENV{GITHUB_OUTPUT} "repo=${repo2}\n")
|
||||
|
||||
- name: use cache
|
||||
id: cache-ccache
|
||||
uses: zephyrproject-rtos/action-s3-cache@v1.2.0
|
||||
with:
|
||||
key: ${{ steps.ccache_cache_timestamp.outputs.repo }}-${{ github.ref_name }}-clang-${{ matrix.platform }}-ccache
|
||||
path: /github/home/.cache/ccache
|
||||
aws-s3-bucket: ccache.zephyrproject.org
|
||||
aws-access-key-id: ${{ vars.AWS_CCACHE_ACCESS_KEY_ID }}
|
||||
aws-secret-access-key: ${{ secrets.AWS_CCACHE_SECRET_ACCESS_KEY }}
|
||||
aws-region: us-east-2
|
||||
|
||||
- name: ccache stats initial
|
||||
run: |
|
||||
mkdir -p /github/home/.cache
|
||||
test -d github/home/.cache/ccache && rm -rf /github/home/.cache/ccache && mv github/home/.cache/ccache /github/home/.cache/ccache
|
||||
ccache -M 10G -s
|
||||
mkdir -p ${CCACHE_DIR}
|
||||
ccache -M 10G
|
||||
ccache -p
|
||||
ccache -z -s -vv
|
||||
|
||||
- name: Run Tests with Twister
|
||||
id: twister
|
||||
@@ -118,10 +107,10 @@ jobs:
|
||||
echo "report_needed=0" >> $GITHUB_OUTPUT
|
||||
fi
|
||||
|
||||
- name: ccache stats post
|
||||
- name: Print ccache stats
|
||||
if: always()
|
||||
run: |
|
||||
ccache -s
|
||||
ccache -p
|
||||
ccache -s -vv
|
||||
|
||||
- name: Upload Unit Test Results
|
||||
if: always() && steps.twister.outputs.report_needed != 0
|
||||
|
||||
58
.github/workflows/codecov.yaml
vendored
58
.github/workflows/codecov.yaml
vendored
@@ -10,19 +10,23 @@ concurrency:
|
||||
|
||||
jobs:
|
||||
codecov:
|
||||
if: github.repository == 'zephyrproject-rtos/zephyr'
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
if: github.repository_owner == 'zephyrproject-rtos'
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
container:
|
||||
image: ghcr.io/zephyrproject-rtos/ci:v0.26.5
|
||||
image: ghcr.io/zephyrproject-rtos/ci-repo-cache:v0.26.5.20231213
|
||||
options: '--entrypoint /bin/bash'
|
||||
volumes:
|
||||
- /repo-cache/zephyrproject:/github/cache/zephyrproject
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
platform: ["native_posix", "qemu_x86", "unit_testing"]
|
||||
env:
|
||||
ZEPHYR_SDK_INSTALL_DIR: /opt/toolchains/zephyr-sdk-0.16.3
|
||||
CCACHE_DIR: /node-cache/ccache-zephyr
|
||||
CCACHE_REMOTE_STORAGE: "redis://cache-*.keydb-cache.svc.cluster.local|shards=1,2,3"
|
||||
CCACHE_REMOTE_ONLY: "true"
|
||||
# `--specs` is ignored because ccache is unable to resovle the toolchain specs file path.
|
||||
CCACHE_IGNOREOPTIONS: '--specs=*'
|
||||
steps:
|
||||
- name: Apply container owner mismatch workaround
|
||||
run: |
|
||||
@@ -32,6 +36,12 @@ jobs:
|
||||
# GitHub comes up with a fundamental fix for this problem.
|
||||
git config --global --add safe.directory ${GITHUB_WORKSPACE}
|
||||
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: Update PATH for west
|
||||
run: |
|
||||
echo "$HOME/.local/bin" >> $GITHUB_PATH
|
||||
@@ -39,7 +49,7 @@ jobs:
|
||||
- name: Clone cached Zephyr repository
|
||||
continue-on-error: true
|
||||
run: |
|
||||
git clone --shared /github/cache/zephyrproject/zephyr .
|
||||
git clone --shared /repo-cache/zephyrproject/zephyr .
|
||||
git remote set-url origin ${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}
|
||||
|
||||
- name: checkout
|
||||
@@ -57,30 +67,13 @@ jobs:
|
||||
cmake --version
|
||||
gcc --version
|
||||
ls -la
|
||||
- name: Prepare ccache keys
|
||||
id: ccache_cache_prop
|
||||
shell: cmake -P {0}
|
||||
run: |
|
||||
string(REPLACE "/" "_" repo ${{github.repository}})
|
||||
string(REPLACE "-" "_" repo2 ${repo})
|
||||
file(APPEND $ENV{GITHUB_OUTPUT} "repo=${repo2}\n")
|
||||
|
||||
- name: use cache
|
||||
id: cache-ccache
|
||||
uses: zephyrproject-rtos/action-s3-cache@v1.2.0
|
||||
with:
|
||||
key: ${{ steps.ccache_cache_prop.outputs.repo }}-${{github.event_name}}-${{matrix.platform}}-codecov-ccache
|
||||
path: /github/home/.cache/ccache
|
||||
aws-s3-bucket: ccache.zephyrproject.org
|
||||
aws-access-key-id: ${{ vars.AWS_CCACHE_ACCESS_KEY_ID }}
|
||||
aws-secret-access-key: ${{ secrets.AWS_CCACHE_SECRET_ACCESS_KEY }}
|
||||
aws-region: us-east-2
|
||||
|
||||
- name: ccache stats initial
|
||||
- name: Set up ccache
|
||||
run: |
|
||||
mkdir -p /github/home/.cache
|
||||
test -d github/home/.cache/ccache && mv github/home/.cache/ccache /github/home/.cache/ccache
|
||||
ccache -M 10G -s
|
||||
mkdir -p ${CCACHE_DIR}
|
||||
ccache -M 10G
|
||||
ccache -p
|
||||
ccache -z -s -vv
|
||||
|
||||
- name: Run Tests with Twister (Push)
|
||||
continue-on-error: true
|
||||
@@ -88,7 +81,8 @@ jobs:
|
||||
export ZEPHYR_BASE=${PWD}
|
||||
export ZEPHYR_TOOLCHAIN_VARIANT=zephyr
|
||||
mkdir -p coverage/reports
|
||||
./scripts/twister --force-color -N -v --filter runnable -p ${{ matrix.platform }} --coverage -T tests
|
||||
./scripts/twister --force-color -N -v --filter runnable -p ${{ matrix.platform }} \
|
||||
--coverage -T tests --timeout-multiplier 2
|
||||
|
||||
- name: Generate Coverage Report
|
||||
run: |
|
||||
@@ -98,10 +92,10 @@ jobs:
|
||||
--remove lcov.pre.info *generated* \
|
||||
-o coverage/reports/${{ matrix.platform }}.info --rc lcov_branch_coverage=1
|
||||
|
||||
- name: ccache stats post
|
||||
- name: Print ccache stats
|
||||
if: always()
|
||||
run: |
|
||||
ccache -s
|
||||
ccache -p
|
||||
ccache -s -vv
|
||||
|
||||
- name: Upload Coverage Results
|
||||
if: always()
|
||||
|
||||
48
.github/workflows/doc-build.yml
vendored
48
.github/workflows/doc-build.yml
vendored
@@ -35,13 +35,29 @@ env:
|
||||
jobs:
|
||||
doc-build-html:
|
||||
name: "Documentation Build (HTML)"
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
timeout-minutes: 45
|
||||
concurrency:
|
||||
group: doc-build-html-${{ github.ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
steps:
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: install-pkgs
|
||||
run: |
|
||||
sudo apt-get update
|
||||
sudo apt-get install -y wget python3-pip git ninja-build graphviz
|
||||
wget --no-verbose "https://github.com/doxygen/doxygen/releases/download/Release_${DOXYGEN_VERSION//./_}/doxygen-${DOXYGEN_VERSION}.linux.bin.tar.gz"
|
||||
sudo tar xf doxygen-${DOXYGEN_VERSION}.linux.bin.tar.gz -C /opt
|
||||
echo "/opt/doxygen-${DOXYGEN_VERSION}/bin" >> $GITHUB_PATH
|
||||
echo "${HOME}/.local/bin" >> $GITHUB_PATH
|
||||
|
||||
- name: checkout
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
@@ -59,13 +75,22 @@ jobs:
|
||||
git rebase origin/${BASE_REF}
|
||||
git log --graph --oneline HEAD...${PR_HEAD}
|
||||
|
||||
- name: install-pkgs
|
||||
- name: checkout
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
ref: ${{ github.event.pull_request.head.sha }}
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Rebase
|
||||
continue-on-error: true
|
||||
env:
|
||||
BASE_REF: ${{ github.base_ref }}
|
||||
PR_HEAD: ${{ github.event.pull_request.head.sha }}
|
||||
run: |
|
||||
sudo apt-get update
|
||||
sudo apt-get install -y ninja-build graphviz
|
||||
wget --no-verbose "https://github.com/doxygen/doxygen/releases/download/Release_${DOXYGEN_VERSION//./_}/doxygen-${DOXYGEN_VERSION}.linux.bin.tar.gz"
|
||||
tar xf doxygen-${DOXYGEN_VERSION}.linux.bin.tar.gz
|
||||
echo "${PWD}/doxygen-${DOXYGEN_VERSION}/bin" >> $GITHUB_PATH
|
||||
git config --global user.email "actions@zephyrproject.org"
|
||||
git config --global user.name "Github Actions"
|
||||
git rebase origin/${BASE_REF}
|
||||
git log --graph --oneline HEAD...${PR_HEAD}
|
||||
|
||||
- name: cache-pip
|
||||
uses: actions/cache@v3
|
||||
@@ -131,7 +156,8 @@ jobs:
|
||||
doc-build-pdf:
|
||||
name: "Documentation Build (PDF)"
|
||||
if: github.event_name != 'pull_request'
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
container: texlive/texlive:latest
|
||||
timeout-minutes: 60
|
||||
concurrency:
|
||||
@@ -139,6 +165,12 @@ jobs:
|
||||
cancel-in-progress: true
|
||||
|
||||
steps:
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: checkout
|
||||
uses: actions/checkout@v3
|
||||
|
||||
|
||||
11
.github/workflows/footprint-tracking.yml
vendored
11
.github/workflows/footprint-tracking.yml
vendored
@@ -22,10 +22,11 @@ concurrency:
|
||||
|
||||
jobs:
|
||||
footprint-tracking:
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
if: github.repository_owner == 'zephyrproject-rtos'
|
||||
container:
|
||||
image: ghcr.io/zephyrproject-rtos/ci:v0.26.5
|
||||
image: ghcr.io/zephyrproject-rtos/ci-repo-cache:v0.26.5.20231213
|
||||
options: '--entrypoint /bin/bash'
|
||||
strategy:
|
||||
fail-fast: false
|
||||
@@ -41,6 +42,12 @@ jobs:
|
||||
# GitHub comes up with a fundamental fix for this problem.
|
||||
git config --global --add safe.directory ${GITHUB_WORKSPACE}
|
||||
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: Update PATH for west
|
||||
run: |
|
||||
echo "$HOME/.local/bin" >> $GITHUB_PATH
|
||||
|
||||
11
.github/workflows/footprint.yml
vendored
11
.github/workflows/footprint.yml
vendored
@@ -8,10 +8,11 @@ concurrency:
|
||||
|
||||
jobs:
|
||||
footprint-delta:
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
if: github.repository == 'zephyrproject-rtos/zephyr'
|
||||
container:
|
||||
image: ghcr.io/zephyrproject-rtos/ci:v0.26.5
|
||||
image: ghcr.io/zephyrproject-rtos/ci-repo-cache:v0.26.5.20231213
|
||||
options: '--entrypoint /bin/bash'
|
||||
strategy:
|
||||
fail-fast: false
|
||||
@@ -27,6 +28,12 @@ jobs:
|
||||
# GitHub comes up with a fundamental fix for this problem.
|
||||
git config --global --add safe.directory ${GITHUB_WORKSPACE}
|
||||
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: Update PATH for west
|
||||
run: |
|
||||
echo "$HOME/.local/bin" >> $GITHUB_PATH
|
||||
|
||||
80
.github/workflows/twister.yaml
vendored
80
.github/workflows/twister.yaml
vendored
@@ -22,19 +22,18 @@ concurrency:
|
||||
jobs:
|
||||
twister-build-prep:
|
||||
if: github.repository_owner == 'zephyrproject-rtos'
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
container:
|
||||
image: ghcr.io/zephyrproject-rtos/ci:v0.26.5
|
||||
image: ghcr.io/zephyrproject-rtos/ci-repo-cache:v0.26.5.20231213
|
||||
options: '--entrypoint /bin/bash'
|
||||
volumes:
|
||||
- /repo-cache/zephyrproject:/github/cache/zephyrproject
|
||||
outputs:
|
||||
subset: ${{ steps.output-services.outputs.subset }}
|
||||
size: ${{ steps.output-services.outputs.size }}
|
||||
fullrun: ${{ steps.output-services.outputs.fullrun }}
|
||||
env:
|
||||
MATRIX_SIZE: 10
|
||||
PUSH_MATRIX_SIZE: 15
|
||||
PUSH_MATRIX_SIZE: 20
|
||||
DAILY_MATRIX_SIZE: 80
|
||||
ZEPHYR_SDK_INSTALL_DIR: /opt/toolchains/zephyr-sdk-0.16.3
|
||||
BSIM_OUT_PATH: /opt/bsim/
|
||||
@@ -51,11 +50,17 @@ jobs:
|
||||
# GitHub comes up with a fundamental fix for this problem.
|
||||
git config --global --add safe.directory ${GITHUB_WORKSPACE}
|
||||
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: Clone cached Zephyr repository
|
||||
if: github.event_name == 'pull_request_target'
|
||||
continue-on-error: true
|
||||
run: |
|
||||
git clone --shared /github/cache/zephyrproject/zephyr .
|
||||
git clone --shared /repo-cache/zephyrproject/zephyr .
|
||||
git remote set-url origin ${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}
|
||||
|
||||
- name: Checkout
|
||||
@@ -77,7 +82,7 @@ jobs:
|
||||
west init -l . || true
|
||||
west config manifest.group-filter -- +ci,+optional
|
||||
west config --global update.narrow true
|
||||
west update --path-cache /github/cache/zephyrproject 2>&1 1> west.update.log || west update --path-cache /github/cache/zephyrproject 2>&1 1> west.update.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /github/cache/zephyrproject)
|
||||
west update --path-cache /repo-cache/zephyrproject 2>&1 1> west.update.log || west update --path-cache /repo-cache/zephyrproject 2>&1 1> west.update.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /repo-cache/zephyrproject)
|
||||
west forall -c 'git reset --hard HEAD'
|
||||
|
||||
- name: Generate Test Plan with Twister
|
||||
@@ -118,29 +123,40 @@ jobs:
|
||||
echo "fullrun=${TWISTER_FULL}" >> $GITHUB_OUTPUT
|
||||
|
||||
twister-build:
|
||||
runs-on: zephyr-runner-linux-x64-4xlarge
|
||||
runs-on:
|
||||
group: zephyr-runner-v2-linux-x64-4xlarge
|
||||
needs: twister-build-prep
|
||||
if: needs.twister-build-prep.outputs.size != 0
|
||||
container:
|
||||
image: ghcr.io/zephyrproject-rtos/ci:v0.26.5
|
||||
image: ghcr.io/zephyrproject-rtos/ci-repo-cache:v0.26.5.20231213
|
||||
options: '--entrypoint /bin/bash'
|
||||
volumes:
|
||||
- /repo-cache/zephyrproject:/github/cache/zephyrproject
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
subset: ${{fromJSON(needs.twister-build-prep.outputs.subset)}}
|
||||
timeout-minutes: 1440
|
||||
env:
|
||||
ZEPHYR_SDK_INSTALL_DIR: /opt/toolchains/zephyr-sdk-0.16.3
|
||||
CCACHE_DIR: /node-cache/ccache-zephyr
|
||||
CCACHE_REMOTE_STORAGE: "redis://cache-*.keydb-cache.svc.cluster.local|shards=1,2,3"
|
||||
CCACHE_REMOTE_ONLY: "true"
|
||||
# `--specs` is ignored because ccache is unable to resolve the toolchain specs file path.
|
||||
CCACHE_IGNOREOPTIONS: '--specs=*'
|
||||
BSIM_OUT_PATH: /opt/bsim/
|
||||
BSIM_COMPONENTS_PATH: /opt/bsim/components
|
||||
TWISTER_COMMON: ' --force-color --inline-logs -v -N -M --retry-failed 3 '
|
||||
TWISTER_COMMON: ' --force-color --inline-logs -v -N -M --retry-failed 3 --timeout-multiplier 2 '
|
||||
DAILY_OPTIONS: ' -M --build-only --all --show-footprint'
|
||||
PR_OPTIONS: ' --clobber-output --integration'
|
||||
PUSH_OPTIONS: ' --clobber-output -M --show-footprint'
|
||||
COMMIT_RANGE: ${{ github.event.pull_request.base.sha }}..${{ github.event.pull_request.head.sha }}
|
||||
BASE_REF: ${{ github.base_ref }}
|
||||
steps:
|
||||
- name: Print cloud service information
|
||||
run: |
|
||||
echo "ZEPHYR_RUNNER_CLOUD_PROVIDER = ${ZEPHYR_RUNNER_CLOUD_PROVIDER}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_NODE = ${ZEPHYR_RUNNER_CLOUD_NODE}"
|
||||
echo "ZEPHYR_RUNNER_CLOUD_POD = ${ZEPHYR_RUNNER_CLOUD_POD}"
|
||||
|
||||
- name: Apply container owner mismatch workaround
|
||||
run: |
|
||||
# FIXME: The owner UID of the GITHUB_WORKSPACE directory may not
|
||||
@@ -152,7 +168,7 @@ jobs:
|
||||
- name: Clone cached Zephyr repository
|
||||
continue-on-error: true
|
||||
run: |
|
||||
git clone --shared /github/cache/zephyrproject/zephyr .
|
||||
git clone --shared /repo-cache/zephyrproject/zephyr .
|
||||
git remote set-url origin ${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}
|
||||
|
||||
- name: Checkout
|
||||
@@ -176,7 +192,7 @@ jobs:
|
||||
west init -l . || true
|
||||
west config manifest.group-filter -- +ci,+optional
|
||||
west config --global update.narrow true
|
||||
west update --path-cache /github/cache/zephyrproject 2>&1 1> west.update.log || west update --path-cache /github/cache/zephyrproject 2>&1 1> west.update.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /github/cache/zephyrproject)
|
||||
west update --path-cache /repo-cache/zephyrproject 2>&1 1> west.update.log || west update --path-cache /repo-cache/zephyrproject 2>&1 1> west.update.log || ( rm -rf ../modules ../bootloader ../tools && west update --path-cache /repo-cache/zephyrproject)
|
||||
west forall -c 'git reset --hard HEAD'
|
||||
|
||||
- name: Check Environment
|
||||
@@ -188,32 +204,12 @@ jobs:
|
||||
echo "github.base_ref: ${{ github.base_ref }}"
|
||||
echo "github.ref_name: ${{ github.ref_name }}"
|
||||
|
||||
- name: Prepare ccache timestamp/data
|
||||
id: ccache_cache_timestamp
|
||||
shell: cmake -P {0}
|
||||
- name: Set up ccache
|
||||
run: |
|
||||
string(TIMESTAMP current_date "%Y-%m-%d-%H;%M;%S" UTC)
|
||||
string(REPLACE "/" "_" repo ${{github.repository}})
|
||||
string(REPLACE "-" "_" repo2 ${repo})
|
||||
file(APPEND $ENV{GITHUB_OUTPUT} "repo=${repo2}\n")
|
||||
|
||||
- name: use cache
|
||||
id: cache-ccache
|
||||
uses: zephyrproject-rtos/action-s3-cache@v1.2.0
|
||||
continue-on-error: true
|
||||
with:
|
||||
key: ${{ steps.ccache_cache_timestamp.outputs.repo }}-${{ github.ref_name }}-${{github.event_name}}-${{ matrix.subset }}-ccache
|
||||
path: /github/home/.cache/ccache
|
||||
aws-s3-bucket: ccache.zephyrproject.org
|
||||
aws-access-key-id: ${{ vars.AWS_CCACHE_ACCESS_KEY_ID }}
|
||||
aws-secret-access-key: ${{ secrets.AWS_CCACHE_SECRET_ACCESS_KEY }}
|
||||
aws-region: us-east-2
|
||||
|
||||
- name: ccache stats initial
|
||||
run: |
|
||||
mkdir -p /github/home/.cache
|
||||
test -d github/home/.cache/ccache && rm -rf /github/home/.cache/ccache && mv github/home/.cache/ccache /github/home/.cache/ccache
|
||||
ccache -M 10G -s
|
||||
mkdir -p ${CCACHE_DIR}
|
||||
ccache -M 10G
|
||||
ccache -p
|
||||
ccache -z -s -vv
|
||||
|
||||
- if: github.event_name == 'push'
|
||||
name: Run Tests with Twister (Push)
|
||||
@@ -256,10 +252,10 @@ jobs:
|
||||
fi
|
||||
fi
|
||||
|
||||
- name: ccache stats post
|
||||
- name: Print ccache stats
|
||||
if: always()
|
||||
run: |
|
||||
ccache -p
|
||||
ccache -s
|
||||
ccache -s -vv
|
||||
|
||||
- name: Upload Unit Test Results
|
||||
if: always()
|
||||
|
||||
@@ -731,6 +731,14 @@ static inline void add_arm_mmu_region(struct arm_mmu_ptables *ptables,
|
||||
|
||||
static inline void inv_dcache_after_map_helper(void *virt, size_t size, uint32_t attrs)
|
||||
{
|
||||
/*
|
||||
* DC IVAC instruction requires write access permission to the VA,
|
||||
* otherwise it can generate a permission fault
|
||||
*/
|
||||
if ((attrs & MT_RW) != MT_RW) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (MT_TYPE(attrs) == MT_NORMAL || MT_TYPE(attrs) == MT_NORMAL_WT) {
|
||||
sys_cache_data_invd_range(virt, size);
|
||||
}
|
||||
@@ -987,6 +995,7 @@ void arch_mem_map(void *virt, uintptr_t phys, size_t size, uint32_t flags)
|
||||
case K_MEM_CACHE_WB:
|
||||
case K_MEM_CACHE_WT:
|
||||
mem_flags = (mem_flags == K_MEM_CACHE_WB) ? MT_NORMAL : MT_NORMAL_WT;
|
||||
mem_flags |= (flags & K_MEM_PERM_RW) ? MT_RW : 0;
|
||||
inv_dcache_after_map_helper(virt, size, mem_flags);
|
||||
default:
|
||||
break;
|
||||
|
||||
@@ -1,448 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 2020 Intel Corporation
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#include <zephyr/kernel.h>
|
||||
#include <zephyr/arch/x86/acpi.h>
|
||||
#include <zephyr/arch/x86/efi.h>
|
||||
|
||||
static struct acpi_rsdp *rsdp;
|
||||
static bool is_rsdp_searched;
|
||||
|
||||
static struct acpi_dmar *dmar;
|
||||
static bool is_dmar_searched;
|
||||
|
||||
static bool check_sum(struct acpi_sdt *t)
|
||||
{
|
||||
uint8_t sum = 0U, *p = (uint8_t *)t;
|
||||
|
||||
for (int i = 0; i < t->length; i++) {
|
||||
sum += p[i];
|
||||
}
|
||||
|
||||
return sum == 0U;
|
||||
}
|
||||
|
||||
static void find_rsdp(void)
|
||||
{
|
||||
uint8_t *bda_seg, *zero_page_base;
|
||||
uint64_t *search;
|
||||
uintptr_t search_phys, rsdp_phys;
|
||||
size_t search_length = 0U, rsdp_length;
|
||||
|
||||
if (is_rsdp_searched) {
|
||||
/* Looking up for RSDP has already been done */
|
||||
return;
|
||||
}
|
||||
|
||||
/* Let's first get it from EFI, if enabled */
|
||||
if (IS_ENABLED(CONFIG_X86_EFI)) {
|
||||
rsdp_phys = (uintptr_t)efi_get_acpi_rsdp();
|
||||
if (rsdp_phys != 0UL) {
|
||||
/* See at found label why this is required */
|
||||
search_length = sizeof(struct acpi_rsdp);
|
||||
z_phys_map((uint8_t **)&search, rsdp_phys, search_length, 0);
|
||||
rsdp = (struct acpi_rsdp *)search;
|
||||
|
||||
goto found;
|
||||
}
|
||||
}
|
||||
|
||||
/* We never identity map the NULL page, so need to map it before
|
||||
* it can be accessed.
|
||||
*/
|
||||
z_phys_map(&zero_page_base, 0, 4096, 0);
|
||||
|
||||
/* Physical (real mode!) address 0000:040e stores a (real
|
||||
* mode!!) segment descriptor pointing to the 1kb Extended
|
||||
* BIOS Data Area.
|
||||
*
|
||||
* We had to memory map this segment descriptor since it is in
|
||||
* the NULL page. The remaining structures (EBDA etc) are identity
|
||||
* mapped somewhere within the minefield of reserved regions in the
|
||||
* first megabyte and are directly accessible.
|
||||
*/
|
||||
bda_seg = 0x040e + zero_page_base;
|
||||
search_phys = (long)(((int)*(uint16_t *)bda_seg) << 4);
|
||||
|
||||
/* Unmap after use */
|
||||
z_phys_unmap(zero_page_base, 4096);
|
||||
|
||||
/* Might be nothing there, check before we inspect.
|
||||
* Note that EBDA usually is in 0x80000 to 0x100000.
|
||||
*/
|
||||
if ((POINTER_TO_UINT(search_phys) >= 0x80000UL) &&
|
||||
(POINTER_TO_UINT(search_phys) < 0x100000UL)) {
|
||||
search_length = 1024;
|
||||
z_phys_map((uint8_t **)&search, search_phys, search_length, 0);
|
||||
|
||||
for (int i = 0; i < 1024/8; i++) {
|
||||
if (search[i] == ACPI_RSDP_SIGNATURE) {
|
||||
rsdp_phys = search_phys + i * 8;
|
||||
rsdp = (void *)&search[i];
|
||||
goto found;
|
||||
}
|
||||
}
|
||||
|
||||
z_phys_unmap((uint8_t *)search, search_length);
|
||||
}
|
||||
|
||||
/* If it's not there, then look for it in the last 128kb of
|
||||
* real mode memory.
|
||||
*/
|
||||
search_phys = 0xe0000;
|
||||
search_length = 128 * 1024;
|
||||
z_phys_map((uint8_t **)&search, search_phys, search_length, 0);
|
||||
|
||||
for (int i = 0; i < 128*1024/8; i++) {
|
||||
if (search[i] == ACPI_RSDP_SIGNATURE) {
|
||||
rsdp_phys = search_phys + i * 8;
|
||||
rsdp = (void *)&search[i];
|
||||
goto found;
|
||||
}
|
||||
}
|
||||
|
||||
z_phys_unmap((uint8_t *)search, search_length);
|
||||
|
||||
rsdp = NULL;
|
||||
|
||||
is_rsdp_searched = true;
|
||||
|
||||
return;
|
||||
|
||||
found:
|
||||
/* Determine length of RSDP table.
|
||||
* ACPI v2 and above uses the length field.
|
||||
* Otherwise, just the size of struct itself.
|
||||
*/
|
||||
if (rsdp->revision < 2) {
|
||||
rsdp_length = sizeof(*rsdp);
|
||||
} else {
|
||||
rsdp_length = rsdp->length;
|
||||
}
|
||||
|
||||
/* Need to unmap search since it is still mapped */
|
||||
if (search_length != 0U) {
|
||||
z_phys_unmap((uint8_t *)search, search_length);
|
||||
}
|
||||
|
||||
/* Now map the RSDP */
|
||||
z_phys_map((uint8_t **)&rsdp, rsdp_phys, rsdp_length, 0);
|
||||
|
||||
is_rsdp_searched = true;
|
||||
}
|
||||
|
||||
void *z_acpi_find_table(uint32_t signature)
|
||||
{
|
||||
uint8_t *mapped_tbl;
|
||||
uint32_t length;
|
||||
struct acpi_rsdt *rsdt;
|
||||
struct acpi_xsdt *xsdt;
|
||||
struct acpi_sdt *t;
|
||||
uintptr_t t_phys;
|
||||
bool tbl_found;
|
||||
|
||||
find_rsdp();
|
||||
|
||||
if (!rsdp) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (rsdp->rsdt_ptr != 0U) {
|
||||
z_phys_map((uint8_t **)&rsdt, rsdp->rsdt_ptr, sizeof(*rsdt), 0);
|
||||
tbl_found = false;
|
||||
|
||||
if (check_sum(&rsdt->sdt)) {
|
||||
/* Remap the memory to the indicated length of RSDT */
|
||||
length = rsdt->sdt.length;
|
||||
z_phys_unmap((uint8_t *)rsdt, sizeof(*rsdt));
|
||||
z_phys_map((uint8_t **)&rsdt, rsdp->rsdt_ptr, length, 0);
|
||||
|
||||
uint32_t *end = (uint32_t *)((char *)rsdt + rsdt->sdt.length);
|
||||
|
||||
/* Extra indirection required to avoid
|
||||
* -Waddress-of-packed-member
|
||||
*/
|
||||
void *table_ptrs = &rsdt->table_ptrs[0];
|
||||
|
||||
for (uint32_t *tp = table_ptrs; tp < end; tp++) {
|
||||
t_phys = (long)*tp;
|
||||
z_phys_map(&mapped_tbl, t_phys, sizeof(*t), 0);
|
||||
t = (void *)mapped_tbl;
|
||||
|
||||
if (t->signature == signature && check_sum(t)) {
|
||||
tbl_found = true;
|
||||
break;
|
||||
}
|
||||
|
||||
z_phys_unmap(mapped_tbl, sizeof(*t));
|
||||
}
|
||||
}
|
||||
|
||||
z_phys_unmap((uint8_t *)rsdt, sizeof(*rsdt));
|
||||
|
||||
if (tbl_found) {
|
||||
goto found;
|
||||
}
|
||||
}
|
||||
|
||||
if (rsdp->revision < 2) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (rsdp->xsdt_ptr != 0ULL) {
|
||||
z_phys_map((uint8_t **)&xsdt, rsdp->xsdt_ptr, sizeof(*xsdt), 0);
|
||||
|
||||
tbl_found = false;
|
||||
if (check_sum(&xsdt->sdt)) {
|
||||
/* Remap the memory to the indicated length of RSDT */
|
||||
length = xsdt->sdt.length;
|
||||
z_phys_unmap((uint8_t *)xsdt, sizeof(*xsdt));
|
||||
z_phys_map((uint8_t **)&xsdt, rsdp->xsdt_ptr, length, 0);
|
||||
|
||||
uint64_t *end = (uint64_t *)((char *)xsdt + xsdt->sdt.length);
|
||||
|
||||
/* Extra indirection required to avoid
|
||||
* -Waddress-of-packed-member
|
||||
*/
|
||||
void *table_ptrs = &xsdt->table_ptrs[0];
|
||||
|
||||
for (uint64_t *tp = table_ptrs; tp < end; tp++) {
|
||||
t_phys = (long)*tp;
|
||||
z_phys_map(&mapped_tbl, t_phys, sizeof(*t), 0);
|
||||
t = (void *)mapped_tbl;
|
||||
|
||||
if (t->signature == signature && check_sum(t)) {
|
||||
tbl_found = true;
|
||||
break;
|
||||
}
|
||||
|
||||
z_phys_unmap(mapped_tbl, sizeof(*t));
|
||||
}
|
||||
}
|
||||
|
||||
z_phys_unmap((uint8_t *)xsdt, sizeof(*xsdt));
|
||||
|
||||
if (tbl_found) {
|
||||
goto found;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
|
||||
found:
|
||||
/* Remap to indicated length of the table */
|
||||
length = t->length;
|
||||
z_phys_unmap(mapped_tbl, sizeof(*t));
|
||||
z_phys_map(&mapped_tbl, t_phys, length, 0);
|
||||
t = (void *)mapped_tbl;
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
/*
|
||||
* Return the 'n'th CPU entry from the ACPI MADT, or NULL if not available.
|
||||
*/
|
||||
|
||||
struct acpi_cpu *z_acpi_get_cpu(int n)
|
||||
{
|
||||
struct acpi_madt *madt = z_acpi_find_table(ACPI_MADT_SIGNATURE);
|
||||
uintptr_t base = POINTER_TO_UINT(madt);
|
||||
uintptr_t offset;
|
||||
|
||||
if (!madt) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
offset = POINTER_TO_UINT(madt->entries) - base;
|
||||
|
||||
while (offset < madt->sdt.length) {
|
||||
struct acpi_madt_entry *entry;
|
||||
|
||||
entry = (struct acpi_madt_entry *)(offset + base);
|
||||
if (entry->type == ACPI_MADT_ENTRY_CPU) {
|
||||
struct acpi_cpu *cpu = (struct acpi_cpu *)entry;
|
||||
|
||||
if ((cpu->flags & ACPI_CPU_FLAGS_ENABLED) != 0) {
|
||||
if (n == 0) {
|
||||
return cpu;
|
||||
}
|
||||
|
||||
--n;
|
||||
}
|
||||
}
|
||||
|
||||
offset += entry->length;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void find_dmar(void)
|
||||
{
|
||||
if (is_dmar_searched) {
|
||||
return;
|
||||
}
|
||||
|
||||
dmar = z_acpi_find_table(ACPI_DMAR_SIGNATURE);
|
||||
is_dmar_searched = true;
|
||||
}
|
||||
|
||||
struct acpi_dmar *z_acpi_find_dmar(void)
|
||||
{
|
||||
find_dmar();
|
||||
return dmar;
|
||||
}
|
||||
|
||||
struct acpi_drhd *z_acpi_find_drhds(int *n)
|
||||
{
|
||||
struct acpi_drhd *drhds = NULL;
|
||||
uintptr_t offset;
|
||||
uintptr_t base;
|
||||
|
||||
find_dmar();
|
||||
|
||||
if (dmar == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
*n = 0;
|
||||
base = POINTER_TO_UINT(dmar);
|
||||
|
||||
offset = POINTER_TO_UINT(dmar->remap_entries) - base;
|
||||
while (offset < dmar->sdt.length) {
|
||||
struct acpi_dmar_entry *entry;
|
||||
|
||||
entry = (struct acpi_dmar_entry *)(offset + base);
|
||||
if (entry->type == ACPI_DMAR_TYPE_DRHD) {
|
||||
if (*n == 0) {
|
||||
drhds = (struct acpi_drhd *)entry;
|
||||
}
|
||||
|
||||
(*n)++;
|
||||
} else {
|
||||
/* DMAR entries are found packed by type so
|
||||
* if type is not DRHD, we will not encounter one,
|
||||
* anymore.
|
||||
*/
|
||||
break;
|
||||
}
|
||||
|
||||
offset += entry->length;
|
||||
}
|
||||
|
||||
return drhds;
|
||||
}
|
||||
|
||||
struct acpi_dmar_dev_scope *z_acpi_get_drhd_dev_scopes(struct acpi_drhd *drhd,
|
||||
int *n)
|
||||
{
|
||||
uintptr_t offset;
|
||||
uintptr_t base;
|
||||
|
||||
if (drhd->entry.length <= ACPI_DRHD_MIN_SIZE) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
*n = 0;
|
||||
base = POINTER_TO_UINT(drhd);
|
||||
|
||||
offset = POINTER_TO_UINT(drhd->device_scope) - base;
|
||||
while (offset < drhd->entry.length) {
|
||||
struct acpi_dmar_dev_scope *dev_scope;
|
||||
|
||||
dev_scope = (struct acpi_dmar_dev_scope *)(offset + base);
|
||||
|
||||
(*n)++;
|
||||
|
||||
offset += dev_scope->length;
|
||||
}
|
||||
|
||||
return (*n == 0) ? NULL : drhd->device_scope;
|
||||
}
|
||||
|
||||
struct acpi_dmar_dev_path *
|
||||
z_acpi_get_dev_scope_paths(struct acpi_dmar_dev_scope *dev_scope, int *n)
|
||||
{
|
||||
switch (dev_scope->type) {
|
||||
case ACPI_DRHD_DEV_SCOPE_PCI_EPD:
|
||||
/* Fall through */
|
||||
case ACPI_DRHD_DEV_SCOPE_PCI_SUB_H:
|
||||
/* Fall through */
|
||||
case ACPI_DRHD_DEV_SCOPE_IOAPIC:
|
||||
if (dev_scope->length < (ACPI_DMAR_DEV_SCOPE_MIN_SIZE +
|
||||
ACPI_DMAR_DEV_PATH_SIZE)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
break;
|
||||
case ACPI_DRHD_DEV_SCOPE_MSI_CAP_HPET:
|
||||
/* Fall through */
|
||||
case ACPI_DRHD_DEV_SCOPE_NAMESPACE_DEV:
|
||||
if (dev_scope->length != (ACPI_DMAR_DEV_SCOPE_MIN_SIZE +
|
||||
ACPI_DMAR_DEV_PATH_SIZE)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
break;
|
||||
default:
|
||||
return NULL;
|
||||
}
|
||||
|
||||
*n = (dev_scope->length - ACPI_DMAR_DEV_SCOPE_MIN_SIZE) /
|
||||
ACPI_DMAR_DEV_PATH_SIZE;
|
||||
|
||||
return dev_scope->path;
|
||||
}
|
||||
|
||||
uint16_t z_acpi_get_dev_id_from_dmar(uint8_t dev_scope_type)
|
||||
{
|
||||
struct acpi_drhd *drhd;
|
||||
int n_drhd;
|
||||
|
||||
find_dmar();
|
||||
|
||||
if (dmar == NULL) {
|
||||
return USHRT_MAX;
|
||||
}
|
||||
|
||||
drhd = z_acpi_find_drhds(&n_drhd);
|
||||
|
||||
for (; n_drhd > 0; n_drhd--) {
|
||||
struct acpi_dmar_dev_scope *dev_scope;
|
||||
int n_ds;
|
||||
|
||||
dev_scope = z_acpi_get_drhd_dev_scopes(drhd, &n_ds);
|
||||
for (; n_ds > 0; n_ds--) {
|
||||
if (dev_scope->type == dev_scope_type) {
|
||||
struct acpi_dmar_dev_path *path;
|
||||
int n_path;
|
||||
|
||||
path = z_acpi_get_dev_scope_paths(dev_scope,
|
||||
&n_path);
|
||||
if (n_path > 0) {
|
||||
union acpi_dmar_id id;
|
||||
|
||||
/* Let's over simplify for now:
|
||||
* we don't look for secondary bus
|
||||
* and extra paths. We just stop here.
|
||||
*/
|
||||
|
||||
id.bits.bus = dev_scope->start_bus_num;
|
||||
id.bits.device = path->device;
|
||||
id.bits.function = path->function;
|
||||
|
||||
return id.raw;
|
||||
}
|
||||
}
|
||||
|
||||
dev_scope = (struct acpi_dmar_dev_scope *)(
|
||||
POINTER_TO_UINT(dev_scope) + dev_scope->length);
|
||||
}
|
||||
|
||||
drhd = (struct acpi_drhd *)(POINTER_TO_UINT(drhd) +
|
||||
drhd->entry.length);
|
||||
}
|
||||
|
||||
return USHRT_MAX;
|
||||
}
|
||||
@@ -13,7 +13,6 @@ CONFIG_SERIAL=y
|
||||
CONFIG_UART_INTERRUPT_DRIVEN=y
|
||||
CONFIG_GPIO=y
|
||||
CONFIG_PINCTRL=y
|
||||
CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC=96000000
|
||||
CONFIG_ARM_MPU=y
|
||||
|
||||
CONFIG_RUNTIME_NMI=y
|
||||
|
||||
@@ -13,7 +13,6 @@ CONFIG_SERIAL=y
|
||||
CONFIG_UART_INTERRUPT_DRIVEN=y
|
||||
CONFIG_GPIO=y
|
||||
CONFIG_PINCTRL=y
|
||||
CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC=96000000
|
||||
CONFIG_ARM_MPU=y
|
||||
|
||||
CONFIG_RUNTIME_NMI=y
|
||||
|
||||
@@ -13,7 +13,6 @@ CONFIG_SERIAL=y
|
||||
CONFIG_UART_INTERRUPT_DRIVEN=y
|
||||
CONFIG_GPIO=y
|
||||
CONFIG_PINCTRL=y
|
||||
CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC=96000000
|
||||
CONFIG_ARM_MPU=y
|
||||
CONFIG_HW_STACK_PROTECTION=y
|
||||
|
||||
|
||||
@@ -13,7 +13,6 @@ CONFIG_SERIAL=y
|
||||
CONFIG_UART_INTERRUPT_DRIVEN=y
|
||||
CONFIG_GPIO=y
|
||||
CONFIG_PINCTRL=y
|
||||
CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC=96000000
|
||||
CONFIG_ARM_MPU=y
|
||||
|
||||
CONFIG_RUNTIME_NMI=y
|
||||
|
||||
@@ -12,7 +12,6 @@ CONFIG_UART_CONSOLE=y
|
||||
CONFIG_SERIAL=y
|
||||
CONFIG_UART_INTERRUPT_DRIVEN=y
|
||||
CONFIG_GPIO=y
|
||||
CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC=96000000
|
||||
CONFIG_ARM_MPU=y
|
||||
CONFIG_HW_STACK_PROTECTION=y
|
||||
CONFIG_PINCTRL=y
|
||||
|
||||
@@ -8,7 +8,6 @@ CONFIG_SOC_SERIES_LPC55XXX=y
|
||||
CONFIG_SOC_LPC55S69_CPU1=y
|
||||
CONFIG_BOARD_LPCXPRESSO55S69_CPU1=y
|
||||
CONFIG_GPIO=y
|
||||
CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC=96000000
|
||||
CONFIG_PINCTRL=y
|
||||
|
||||
CONFIG_RUNTIME_NMI=y
|
||||
|
||||
@@ -12,7 +12,6 @@ CONFIG_UART_CONSOLE=y
|
||||
CONFIG_SERIAL=y
|
||||
CONFIG_UART_INTERRUPT_DRIVEN=y
|
||||
CONFIG_GPIO=y
|
||||
CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC=96000000
|
||||
CONFIG_PINCTRL=y
|
||||
|
||||
# TFM sets up MPU_NS, can't correctly change this configuration yet
|
||||
|
||||
@@ -38,6 +38,10 @@
|
||||
};
|
||||
};
|
||||
|
||||
&clk_lsi {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&clk_hse {
|
||||
clock-frequency = <DT_FREQ_M(16)>;
|
||||
status = "okay";
|
||||
@@ -99,3 +103,9 @@ zephyr_udc0: &usbotg_fs {
|
||||
&cryp {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&rtc {
|
||||
clocks = <&rcc STM32_CLOCK_BUS_APB1 0x10000000>,
|
||||
<&rcc STM32_SRC_LSI RTC_SEL(2)>;
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
@@ -36,6 +36,8 @@ config HEAP_MEM_POOL_SIZE
|
||||
default 64000000
|
||||
config MAIN_STACK_SIZE
|
||||
default 320000
|
||||
config ACPI_PRT_BUS_NAME
|
||||
default "_SB.PC00"
|
||||
|
||||
if SHELL
|
||||
config SHELL_STACK_SIZE
|
||||
|
||||
@@ -19,8 +19,12 @@ config SHELL_BACKEND_SERIAL_INTERRUPT_DRIVEN
|
||||
default n
|
||||
endif
|
||||
|
||||
config ACPI_PRT_BUS_NAME
|
||||
depends on ACPI
|
||||
default "_SB.PC00"
|
||||
|
||||
config HEAP_MEM_POOL_SIZE
|
||||
default 32768 if ACPI
|
||||
default 2097152 if ACPI
|
||||
depends on KERNEL_MEM_POOL
|
||||
|
||||
# TSC on this board is 1.9 GHz, HPET and APIC are 19.2 MHz
|
||||
|
||||
@@ -29,6 +29,10 @@ endif
|
||||
config ACPI
|
||||
default y
|
||||
|
||||
config ACPI_PRT_BUS_NAME
|
||||
depends on ACPI
|
||||
default "_SB.PC00"
|
||||
|
||||
if DMA
|
||||
config DMA_64BIT
|
||||
default y
|
||||
|
||||
@@ -25,7 +25,7 @@ config KERNEL_VM_SIZE
|
||||
default 0x10000000 if ACPI
|
||||
|
||||
config HEAP_MEM_POOL_SIZE
|
||||
default 32768 if ACPI
|
||||
default 1048576 if ACPI
|
||||
depends on KERNEL_MEM_POOL
|
||||
|
||||
config MULTIBOOT
|
||||
@@ -54,7 +54,7 @@ config KERNEL_VM_SIZE
|
||||
default 0x10000000 if ACPI
|
||||
|
||||
config HEAP_MEM_POOL_SIZE
|
||||
default 32768 if ACPI
|
||||
default 1048576 if ACPI
|
||||
depends on KERNEL_MEM_POOL
|
||||
|
||||
endif # BOARD_QEMU_X86_64
|
||||
|
||||
@@ -9,7 +9,7 @@ config MP_MAX_NUM_CPUS
|
||||
default 2 if BOARD_UP_SQUARED
|
||||
|
||||
config HEAP_MEM_POOL_SIZE
|
||||
default 32768 if ACPI
|
||||
default 1048576 if ACPI
|
||||
depends on KERNEL_MEM_POOL
|
||||
|
||||
config BUILD_OUTPUT_STRIPPED
|
||||
|
||||
@@ -167,8 +167,8 @@
|
||||
&i2c1 {
|
||||
status = "disabled";
|
||||
clock-frequency = <I2C_BITRATE_STANDARD>;
|
||||
sda-gpios = <&gpio0 32 GPIO_OPEN_DRAIN>;
|
||||
scl-gpios = <&gpio0 33 GPIO_OPEN_DRAIN>;
|
||||
sda-gpios = <&gpio1 0 GPIO_OPEN_DRAIN>;
|
||||
scl-gpios = <&gpio1 1 GPIO_OPEN_DRAIN>;
|
||||
pinctrl-0 = <&i2c1_default>;
|
||||
pinctrl-names = "default";
|
||||
};
|
||||
|
||||
@@ -16,8 +16,8 @@
|
||||
<3 0 &gpio0 4 0>, /* D3 */
|
||||
<4 0 &gpio0 5 0>, /* D4 */
|
||||
<5 0 &gpio0 6 0>, /* D5 */
|
||||
<6 0 &gpio0 43 0>, /* D6 */
|
||||
<7 0 &gpio0 44 0>, /* D7 */
|
||||
<6 0 &gpio1 11 0>, /* D6 */
|
||||
<7 0 &gpio1 12 0>, /* D7 */
|
||||
<8 0 &gpio0 7 0>, /* D8 */
|
||||
<9 0 &gpio0 8 0>, /* D9 */
|
||||
<10 0 &gpio0 9 0>; /* D10 */
|
||||
|
||||
@@ -79,6 +79,10 @@
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&gpio1 {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
&wdt0 {
|
||||
status = "okay";
|
||||
};
|
||||
|
||||
@@ -26,7 +26,11 @@ find_program(CMAKE_OBJCOPY NAMES
|
||||
llvm-objcopy-${CLANGVER}
|
||||
objcopy
|
||||
${find_program_binutils_args})
|
||||
find_program(CMAKE_READELF readelf ${find_program_binutils_args})
|
||||
find_program(CMAKE_READELF NAMES
|
||||
llvm-readelf
|
||||
llvm-readelf-${CLANGVER}
|
||||
readelf
|
||||
${find_program_binutils_args})
|
||||
|
||||
# Use the gnu binutil abstraction
|
||||
include(${ZEPHYR_BASE}/cmake/bintools/llvm/target_bintools.cmake)
|
||||
|
||||
@@ -134,7 +134,7 @@ set(VENDOR_PREFIXES dts/bindings/vendor-prefixes.txt)
|
||||
set_ifndef(DTS_SOURCE ${BOARD_DIR}/${BOARD}.dts)
|
||||
if(EXISTS ${DTS_SOURCE})
|
||||
# We found a devicetree. Check for a board revision overlay.
|
||||
if(BOARD_REVISION AND EXISTS ${BOARD_DIR}/${BOARD}_${BOARD_REVISION_STRING}.overlay)
|
||||
if(DEFINED BOARD_REVISION AND EXISTS ${BOARD_DIR}/${BOARD}_${BOARD_REVISION_STRING}.overlay)
|
||||
list(APPEND DTS_SOURCE ${BOARD_DIR}/${BOARD}_${BOARD_REVISION_STRING}.overlay)
|
||||
endif()
|
||||
else()
|
||||
|
||||
@@ -2095,16 +2095,12 @@ function(toolchain_parse_make_rule input_file include_files)
|
||||
# the element separator, so let's get the pure `;` back.
|
||||
string(REPLACE "\;" ";" input_as_list ${input})
|
||||
|
||||
# Pop the first line and treat it specially
|
||||
list(POP_FRONT input_as_list first_input_line)
|
||||
string(FIND ${first_input_line} ": " index)
|
||||
math(EXPR j "${index} + 2")
|
||||
string(SUBSTRING ${first_input_line} ${j} -1 first_include_file)
|
||||
# The file might also contain multiple files on one line if one or both of
|
||||
# the file paths are short, split these up into multiple elements using regex
|
||||
string(REGEX REPLACE "([^ ])[ ]([^ ])" "\\1;\\2" input_as_list "${input_as_list}")
|
||||
|
||||
# Remove whitespace before and after filename and convert to CMake path.
|
||||
string(STRIP "${first_include_file}" first_include_file)
|
||||
file(TO_CMAKE_PATH "${first_include_file}" first_include_file)
|
||||
set(result "${first_include_file}")
|
||||
# Pop the first item containing "empty_file.o:"
|
||||
list(POP_FRONT input_as_list first_input_line)
|
||||
|
||||
# Remove whitespace before and after filename and convert to CMake path.
|
||||
foreach(file ${input_as_list})
|
||||
|
||||
@@ -71,7 +71,7 @@ REDIRECTS = [
|
||||
('guides/pm/power_domain', 'services/pm/power_domain'),
|
||||
('guides/pm/system', 'services/pm/system'),
|
||||
('guides/portability/index', 'services/portability/index'),
|
||||
('guides/portability/posix', 'services/portability/posix'),
|
||||
('guides/portability/posix', 'services/portability/posix/index'),
|
||||
('guides/porting/arch', 'hardware/porting/arch'),
|
||||
('guides/porting/board_porting', 'hardware/porting/board_porting'),
|
||||
('guides/porting/index', 'hardware/porting/index'),
|
||||
|
||||
@@ -80,6 +80,8 @@ Zephyr offers a large and ever growing number of features including:
|
||||
* Red/black tree ready queue
|
||||
* Traditional multi-queue ready queue
|
||||
|
||||
.. _zephyr_intro_configurability:
|
||||
|
||||
**Highly configurable / Modular for flexibility**
|
||||
Allows an application to incorporate *only* the capabilities it needs as it
|
||||
needs them, and to specify their quantity and size.
|
||||
|
||||
@@ -79,6 +79,25 @@ C Library
|
||||
to a smaller, but inexact conversion algorithm. This requires building
|
||||
Picolibc as a module.
|
||||
|
||||
Optional Modules
|
||||
================
|
||||
|
||||
The following modules have been made optional and are not downloaded with `west update` by default anymore:
|
||||
|
||||
* ``chre``
|
||||
* ``lz4``
|
||||
* ``nanopb``
|
||||
* ``psa-arch-tests``
|
||||
* ``sof``
|
||||
* ``tf-m-tests``
|
||||
* ``tflite-micro``
|
||||
* ``thrift``
|
||||
* ``zscilib``
|
||||
|
||||
To enable them again use the ``west config manifest.project-filter -- +<module
|
||||
name>`` command, or ``west config manifest.group-filter -- +optional`` to
|
||||
enable all optional modules, and then run ``west update`` again.
|
||||
|
||||
Device Drivers and Device Tree
|
||||
==============================
|
||||
|
||||
|
||||
@@ -68,6 +68,9 @@ https://docs.zephyrproject.org/latest/security/vulnerabilities.html
|
||||
* CVE-2023-5563 `Zephyr project bug tracker GHSA-98mc-rj7w-7rpv
|
||||
<https://github.com/zephyrproject-rtos/zephyr/security/advisories/GHSA-98mc-rj7w-7rpv>`_
|
||||
|
||||
* CVE-2023-5753 `Zephyr project bug tracker GHSA-hmpr-px56-rvww
|
||||
<https://github.com/zephyrproject-rtos/zephyr/security/advisories/GHSA-hmpr-px56-rvww>`_
|
||||
|
||||
Kernel
|
||||
******
|
||||
|
||||
|
||||
@@ -1547,3 +1547,17 @@ This has been fixed in main for v3.5.0
|
||||
|
||||
- `PR 63717 fix for 3.3
|
||||
<https://github.com/zephyrproject-rtos/zephyr/pull/63717>`_
|
||||
|
||||
CVE-2023-5753
|
||||
-------------
|
||||
|
||||
Potential buffer overflow vulnerabilities in the Zephyr Bluetooth
|
||||
subsystem source code when asserts are disabled.
|
||||
|
||||
- `Zephyr project bug tracker GHSA-hmpr-px56-rvww
|
||||
<https://github.com/zephyrproject-rtos/zephyr/security/advisories/GHSA-hmpr-px56-rvww>`_
|
||||
|
||||
This has been fixed in main for v3.5.0
|
||||
|
||||
- `PR 63605 fix for main
|
||||
<https://github.com/zephyrproject-rtos/zephyr/pull/63605>`_
|
||||
|
||||
@@ -14,6 +14,6 @@ supported by the Zephyr RTOS.
|
||||
.. toctree::
|
||||
:maxdepth: 1
|
||||
|
||||
posix.rst
|
||||
posix/index.rst
|
||||
cmsis_rtos_v1.rst
|
||||
cmsis_rtos_v2.rst
|
||||
|
||||
191
doc/services/portability/posix/aep/index.rst
Normal file
191
doc/services/portability/posix/aep/index.rst
Normal file
@@ -0,0 +1,191 @@
|
||||
.. _posix_aep:
|
||||
|
||||
POSIX Application Environment Profiles (AEP)
|
||||
############################################
|
||||
|
||||
Although inactive, `IEEE 1003.13-2003`_ defined a number of AEP that inspired the modern
|
||||
subprofiling options of `IEEE 1003.1-2017`_. The single-purpose realtime system profiles
|
||||
are listed below, for reference, in terms that agree with the current POSIX-1 standard. PSE54
|
||||
is not considered at this time.
|
||||
|
||||
.. _posix_aep_pse51:
|
||||
|
||||
Minimal Realtime System Profile (PSE51)
|
||||
=======================================
|
||||
|
||||
.. Conforming implementations shall define _POSIX_AEP_REALTIME_MINIMAL to the value 200312L
|
||||
|
||||
.. csv-table:: PSE51 System Interfaces
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_AEP_REALTIME_MINIMAL, -1,
|
||||
|
||||
.. csv-table:: PSE51 Option Groups
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
POSIX_C_LANG_JUMP,,
|
||||
POSIX_C_LANG_SUPPORT, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_DEVICE_IO,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_FILE_LOCKING,,
|
||||
POSIX_SIGNALS,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_SINGLE_PROCESS,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_THREADS_BASE, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
XSI_THREADS_EXT, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
|
||||
.. csv-table:: PSE51 Option Requirements
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_CLOCK_SELECTION, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_FSYNC, -1,
|
||||
_POSIX_MEMLOCK, -1,
|
||||
_POSIX_MEMLOCK_RANGE, -1,
|
||||
_POSIX_MONOTONIC_CLOCK, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_REALTIME_SIGNALS, -1,
|
||||
_POSIX_SEMAPHORES, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
_POSIX_SHARED_MEMORY_OBJECTS, -1,
|
||||
_POSIX_SYNCHRONIZED_IO, -1,
|
||||
_POSIX_THREAD_ATTR_STACKADDR, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_ATTR_STACKSIZE, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_CPUTIME, -1,
|
||||
_POSIX_THREAD_PRIO_INHERIT, 200809L, :kconfig:option:`CONFIG_PTHREAD_MUTEX`
|
||||
_POSIX_THREAD_PRIO_PROTECT, -1,
|
||||
_POSIX_THREAD_PRIORITY_SCHEDULING, -1,
|
||||
_POSIX_THREAD_SPORADIC_SERVER, -1,
|
||||
_POSIX_TIMEOUTS, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
_POSIX_TIMERS, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
|
||||
.. note::
|
||||
For PSE51 support, 44 of 75 symbols are currently implemented.
|
||||
|
||||
.. _posix_aep_pse52:
|
||||
|
||||
Realtime Controller System Profile (PSE52)
|
||||
==========================================
|
||||
|
||||
.. Conforming implementations shall define _POSIX_AEP_REALTIME_CONTROLLER to the value 200312L
|
||||
|
||||
.. csv-table:: PSE52 System Interfaces
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_AEP_REALTIME_CONTROLLER, -1,
|
||||
|
||||
.. csv-table:: PSE52 Option Groups
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
POSIX_C_LANG_JUMP,,
|
||||
POSIX_C_LANG_MATH, yes,
|
||||
POSIX_C_LANG_SUPPORT, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_DEVICE_IO,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_FD_MGMT,,
|
||||
POSIX_FILE_LOCKING,,
|
||||
POSIX_FILE_SYSTEM,,
|
||||
POSIX_SIGNALS,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_SINGLE_PROCESS,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_THREADS_BASE, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
XSI_THREADS_EXT, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
|
||||
.. csv-table:: PSE52 Option Requirements
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_CLOCK_SELECTION, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_FSYNC, -1,
|
||||
_POSIX_MAPPED_FILES, -1,
|
||||
_POSIX_MEMLOCK, -1,
|
||||
_POSIX_MEMLOCK_RANGE, -1,
|
||||
_POSIX_MESSAGE_PASSING, 200809L, :kconfig:option:`CONFIG_POSIX_MQUEUE`
|
||||
_POSIX_MONOTONIC_CLOCK, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_REALTIME_SIGNALS, -1,
|
||||
_POSIX_SEMAPHORES, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
_POSIX_SHARED_MEMORY_OBJECTS, -1,
|
||||
_POSIX_SYNCHRONIZED_IO, -1,
|
||||
_POSIX_THREAD_ATTR_STACKADDR, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_ATTR_STACKSIZE, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_CPUTIME, -1,
|
||||
_POSIX_THREAD_PRIO_INHERIT, 200809L, :kconfig:option:`CONFIG_PTHREAD_MUTEX`
|
||||
_POSIX_THREAD_PRIO_PROTECT, -1,
|
||||
_POSIX_THREAD_PRIORITY_SCHEDULING, -1,
|
||||
_POSIX_THREAD_SPORADIC_SERVER, -1,
|
||||
_POSIX_TIMEOUTS, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
_POSIX_TIMERS, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_TRACE, -1,
|
||||
_POSIX_TRACE_EVENT_FILTER, -1,
|
||||
_POSIX_TRACE_LOG, -1,
|
||||
|
||||
.. _posix_aep_pse53:
|
||||
|
||||
Dedicated Realtime System Profile (PSE53)
|
||||
=========================================
|
||||
|
||||
.. Conforming implementations shall define _POSIX_AEP_REALTIME_MINIMAL to the value 200312L
|
||||
|
||||
.. csv-table:: PSE53 System Interfaces
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_AEP_REALTIME_CONTROLLER, -1,
|
||||
|
||||
.. csv-table:: PSE53 Option Groups
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
POSIX_C_LANG_JUMP,,
|
||||
POSIX_C_LANG_MATH, yes,
|
||||
POSIX_C_LANG_SUPPORT, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_DEVICE_IO,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_FD_MGMT,,
|
||||
POSIX_FILE_LOCKING,,
|
||||
POSIX_FILE_SYSTEM,,
|
||||
POSIX_MULTI_PROCESS,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_NETWORKING, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_PIPE,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_SIGNALS,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_SIGNAL_JUMP,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_SINGLE_PROCESS,, :ref:`†<posix_undefined_behaviour>`
|
||||
POSIX_THREADS_BASE, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
XSI_THREADS_EXT, yes, :ref:`†<posix_undefined_behaviour>`
|
||||
|
||||
.. csv-table:: PSE53 Option Requirements
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_ASYNCHRONOUS_IO, -1,
|
||||
_POSIX_CLOCK_SELECTION, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_CPUTIME, -1,
|
||||
_POSIX_FSYNC, -1,
|
||||
_POSIX_MAPPED_FILES, -1,
|
||||
_POSIX_MEMLOCK, -1,
|
||||
_POSIX_MEMLOCK_RANGE, -1,
|
||||
_POSIX_MEMORY_PROTECTION, -1,
|
||||
_POSIX_MESSAGE_PASSING, 200809L, :kconfig:option:`CONFIG_POSIX_MQUEUE`
|
||||
_POSIX_MONOTONIC_CLOCK, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_PRIORITIZED_IO, -1,
|
||||
_POSIX_PRIORITY_SCHEDULING, -1,
|
||||
_POSIX_RAW_SOCKETS, 200809L, :kconfig:option:`CONFIG_NET_SOCKETS`
|
||||
_POSIX_REALTIME_SIGNALS, -1,
|
||||
_POSIX_SEMAPHORES, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
_POSIX_SHARED_MEMORY_OBJECTS, -1,
|
||||
_POSIX_SPAWN, -1,
|
||||
_POSIX_SPORADIC_SERVER, -1,
|
||||
_POSIX_SYNCHRONIZED_IO, -1,
|
||||
_POSIX_THREAD_ATTR_STACKADDR, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_ATTR_STACKSIZE, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_CPUTIME, -1,
|
||||
_POSIX_THREAD_PRIO_INHERIT, 200809L, :kconfig:option:`CONFIG_PTHREAD_MUTEX`
|
||||
_POSIX_THREAD_PRIO_PROTECT, -1,
|
||||
_POSIX_THREAD_PRIORITY_SCHEDULING, -1,
|
||||
_POSIX_THREAD_PROCESS_SHARED, -1,
|
||||
_POSIX_THREAD_SPORADIC_SERVER, -1,
|
||||
_POSIX_TIMEOUTS, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
_POSIX_TIMERS, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_TRACE, -1,
|
||||
_POSIX_TRACE_EVENT_FILTER, -1,
|
||||
_POSIX_TRACE_LOG, -1,
|
||||
|
||||
.. _IEEE 1003.1-2017: https://standards.ieee.org/ieee/1003.1/7101/
|
||||
.. _IEEE 1003.13-2003: https://standards.ieee.org/ieee/1003.13/3322/
|
||||
145
doc/services/portability/posix/conformance/index.rst
Normal file
145
doc/services/portability/posix/conformance/index.rst
Normal file
@@ -0,0 +1,145 @@
|
||||
.. _posix_conformance:
|
||||
|
||||
POSIX Conformance
|
||||
#################
|
||||
|
||||
As per `IEEE 1003.1-2017`, this section details Zephyr's POSIX conformance.
|
||||
|
||||
.. _posix_undefined_behaviour:
|
||||
|
||||
.. note::
|
||||
As per POSIX 1003.13, single process mode is supported directly by both PSE51 and PSE52
|
||||
profiles. While Zephyr includes support for many features found in PSE53, PSE53 itself requires
|
||||
supporting multiple processes. Since supporting multiple processes is beyond the scope of
|
||||
Zephyr's current design, some features requiring multi-process capabilities may exhibit
|
||||
undefined behaviour, which we denote with the † (obelus) symbol.
|
||||
|
||||
.. _posix_system_interfaces:
|
||||
|
||||
POSIX System Interfaces
|
||||
=======================
|
||||
|
||||
.. The following have values greater than -1 in Zephyr, conformant with the POSIX specification.
|
||||
|
||||
.. csv-table:: POSIX System Interfaces
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_CHOWN_RESTRICTED, 0,
|
||||
_POSIX_NO_TRUNC, 0,
|
||||
_POSIX_VDISABLE, 0,
|
||||
|
||||
.. The following should be valued greater than zero in Zephyr, in order to be strictly conformant
|
||||
with the POSIX specification.
|
||||
|
||||
.. csv-table:: POSIX System Interfaces
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_JOB_CONTROL, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX_REGEXP, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX_SAVED_IDS, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX_SHELL, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
|
||||
.. TODO: POSIX_ASYNCHRONOUS_IO, and other interfaces below, are mandatory. That means that a
|
||||
strictly conforming application need not be modified in order to compile against Zephyr.
|
||||
However, we may add implementations that simply fail with ENOSYS as long as the functional
|
||||
modification is clearly documented. The implementation is not required for PSE51 or PSE52
|
||||
and beyond that POSIX async I/O functions are rarely used in practice.
|
||||
|
||||
.. csv-table:: POSIX System Interfaces
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_VERSION, 200809L,
|
||||
_POSIX_ASYNCHRONOUS_IO, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
:ref:`_POSIX_BARRIERS<posix_option_group_barriers>`, 200809L, :kconfig:option:`CONFIG_PTHREAD_BARRIER`
|
||||
:ref:`_POSIX_CLOCK_SELECTION<posix_option_group_clock_selection>`, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_MAPPED_FILES, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX_MEMORY_PROTECTION, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
:ref:`_POSIX_READER_WRITER_LOCKS<posix_option_reader_writer_locks>`, -1, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
_POSIX_REALTIME_SIGNALS, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
:ref:`_POSIX_SEMAPHORES<posix_option_group_semaphores>`, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
:ref:`_POSIX_SPIN_LOCKS<posix_option_group_spin_locks>`, 200809L, :kconfig:option:`CONFIG_PTHREAD_SPINLOCK`
|
||||
_POSIX_THREAD_SAFE_FUNCTIONS, 200809L,
|
||||
:ref:`_POSIX_THREADS<posix_option_group_threads_base>`, -1, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
:ref:`_POSIX_TIMEOUTS<posix_option_timeouts>`, 200809L, :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
:ref:`_POSIX_TIMERS<posix_option_group_timers>`, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX2_C_BIND, 200809L,
|
||||
|
||||
.. csv-table:: POSIX System Interfaces (Optional)
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_ADVISORY_INFO, -1,
|
||||
_POSIX_CPUTIME, -1,
|
||||
_POSIX_FSYNC, -1,
|
||||
_POSIX_IPV6, 200809L, :kconfig:option:`CONFIG_NET_IPV6`
|
||||
_POSIX_MEMLOCK, -1,
|
||||
_POSIX_MEMLOCK_RANGE, -1,
|
||||
:ref:`_POSIX_MESSAGE_PASSING<posix_option_message_passing>`, 200809L, :kconfig:option:`CONFIG_POSIX_MQUEUE`
|
||||
_POSIX_MONOTONIC_CLOCK, 200809L, :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
_POSIX_PRIORITIZED_IO, -1,
|
||||
:ref:`_POSIX_PRIORITY_SCHEDULING<posix_option_priority_scheduling>`, -1, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_RAW_SOCKETS, 200809L, :kconfig:option:`CONFIG_NET_SOCKETS`
|
||||
_POSIX_SHARED_MEMORY_OBJECTS, -1,
|
||||
_POSIX_SPAWN, -1,
|
||||
_POSIX_SPORADIC_SERVER, -1,
|
||||
_POSIX_SYNCHRONIZED_IO, -1,
|
||||
:ref:`_POSIX_THREAD_ATTR_STACKADDR<posix_option_thread_attr_stackaddr>`, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_CPUTIME, -1,
|
||||
:ref:`_POSIX_THREAD_ATTR_STACKSIZE<posix_option_thread_attr_stacksize>`, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_PRIO_INHERIT, 200809L, :kconfig:option:`CONFIG_PTHREAD_MUTEX`
|
||||
_POSIX_THREAD_PRIO_PROTECT, -1,
|
||||
:ref:`_POSIX_THREAD_PRIORITY_SCHEDULING<posix_option_thread_priority_scheduling>`, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_PROCESS_SHARED, -1,
|
||||
_POSIX_THREAD_SPORADIC_SERVER, -1,
|
||||
_POSIX_TRACE, -1,
|
||||
_POSIX_TRACE_EVENT_FILTER, -1,
|
||||
_POSIX_TRACE_INHERIT, -1,
|
||||
_POSIX_TRACE_LOG, -1,
|
||||
_POSIX_TYPED_MEMORY_OBJECTS, -1,
|
||||
_XOPEN_CRYPT, -1,
|
||||
_XOPEN_REALTIME, -1,
|
||||
_XOPEN_REALTIME_THREADS, -1,
|
||||
:ref:`_XOPEN_STREAMS<posix_option_xopen_streams>`, -1, :kconfig:option:`CONFIG_NET_SOCKETS`
|
||||
_XOPEN_UNIX, -1,
|
||||
|
||||
POSIX Shell and Utilities
|
||||
=========================
|
||||
|
||||
Zephyr does not support a POSIX shell or utilities at this time.
|
||||
|
||||
.. csv-table:: POSIX Shell and Utilities
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX2_C_DEV, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_CHAR_TERM, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_FORT_DEV, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_FORT_RUN, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_LOCALEDEF, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_PBS, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_PBS_ACCOUNTING, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_PBS_LOCATE, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_PBS_MESSAGE, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_PBS_TRACK, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_SW_DEV, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_UPE, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_UNIX, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
_POSIX2_UUCP, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
|
||||
XSI Conformance
|
||||
###############
|
||||
|
||||
XSI System Interfaces
|
||||
=====================
|
||||
|
||||
.. csv-table:: XSI System Interfaces
|
||||
:header: Symbol, Support, Remarks
|
||||
:widths: 50, 10, 50
|
||||
|
||||
_POSIX_FSYNC, -1, :ref:`†<posix_undefined_behaviour>`
|
||||
:ref:`_POSIX_THREAD_ATTR_STACKADDR<posix_option_thread_attr_stackaddr>`, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
:ref:`_POSIX_THREAD_ATTR_STACKSIZE<posix_option_thread_attr_stacksize>`, 200809L, :kconfig:option:`CONFIG_PTHREAD`
|
||||
_POSIX_THREAD_PROCESS_SHARED, -1,
|
||||
77
doc/services/portability/posix/implementation/index.rst
Normal file
77
doc/services/portability/posix/implementation/index.rst
Normal file
@@ -0,0 +1,77 @@
|
||||
.. _posix_details:
|
||||
|
||||
Implementation Details
|
||||
######################
|
||||
|
||||
In many ways, Zephyr provides support like any POSIX OS; API bindings are provided in the C
|
||||
programming language, POSIX headers are available in the standard include path, when configured.
|
||||
|
||||
Unlike other multi-purpose POSIX operating systems
|
||||
|
||||
- Zephyr is not "a POSIX OS". The Zephyr kernel was not designed around the POSIX standard, and
|
||||
POSIX support is an opt-in feature
|
||||
- Zephyr apps are not linked separately, nor do they execute as subprocesses
|
||||
- Zephyr, libraries, and application code are compiled and linked together, running similarly to
|
||||
a single-process application, in a single (possibly virtual) address space
|
||||
- Zephyr does not provide a POSIX shell, compiler, utilities, and is not self-hosting.
|
||||
|
||||
.. note::
|
||||
Unlike the Linux kernel or FreeBSD, Zephyr does not maintain a static table of system call
|
||||
numbers for each supported architecture, but instead generates system calls dynamically at
|
||||
build time. See `System Calls <syscalls>`_ for more information.
|
||||
|
||||
Design
|
||||
======
|
||||
|
||||
As a library, Zephyr's POSIX API implementation makes an effort to be a thin abstraction layer
|
||||
between the application, middleware, and the Zephyr kernel.
|
||||
|
||||
Some general design considerations:
|
||||
|
||||
- The POSIX interface and implementations should be part of Zephyr's POSIX library, and not
|
||||
elsewhere, unless required both by the POSIX API implementation and some other feature. An
|
||||
example where the implementation should remain part of the POSIX implementation is
|
||||
``getopt()``. Examples where the implementation should be part of separate libraries are
|
||||
multithreading and networking.
|
||||
|
||||
- When the POSIX API and another Zephyr subsystem both rely on a feature, the implementation of
|
||||
that feature should be as a separate Zephyr library that can be used by both the POSIX API and
|
||||
the other library or subsystem. This reduces the likelihood of dependency cycles in code. When
|
||||
practical, that rule should expand to include macros. In the example below, ``libposix``
|
||||
depends on ``libzfoo`` for the implementation of some functionality "foo" in Zephyr. If
|
||||
``libzfoo`` also depends on ``libposix``, then there is a dependency cycle. The cycle can be
|
||||
removed via mutual dependency, ``libcommon``.
|
||||
|
||||
.. graphviz::
|
||||
:caption: Dependency cycle between POSIX and another Zephyr library
|
||||
|
||||
digraph {
|
||||
node [shape=rect, style=rounded];
|
||||
rankdir=LR;
|
||||
|
||||
libposix [fillcolor="#d5e8d4"];
|
||||
libzfoo [fillcolor="#dae8fc"];
|
||||
|
||||
libposix -> libzfoo;
|
||||
libzfoo -> libposix;
|
||||
}
|
||||
|
||||
.. graphviz::
|
||||
:caption: Mutual dependencies between POSIX and other Zephyr libraries
|
||||
|
||||
digraph {
|
||||
node [shape=rect, style=rounded];
|
||||
rankdir=LR;
|
||||
|
||||
libposix [fillcolor="#d5e8d4"];
|
||||
libzfoo [fillcolor="#dae8fc"];
|
||||
libcommon [fillcolor="#f8cecc"];
|
||||
|
||||
libposix -> libzfoo;
|
||||
libposix -> libcommon;
|
||||
libzfoo -> libcommon;
|
||||
}
|
||||
|
||||
- POSIX API calls should be provided as regular callable C functions; if a Zephyr
|
||||
`System Call <syscalls>`_ is needed as part of the implementation, the declaration and the
|
||||
implementation of that system call should be hidden behind the POSIX API.
|
||||
14
doc/services/portability/posix/index.rst
Normal file
14
doc/services/portability/posix/index.rst
Normal file
@@ -0,0 +1,14 @@
|
||||
.. _posix_support:
|
||||
|
||||
POSIX
|
||||
#####
|
||||
|
||||
.. toctree::
|
||||
:maxdepth: 2
|
||||
|
||||
overview/index.rst
|
||||
conformance/index.rst
|
||||
aep/index.rst
|
||||
implementation/index.rst
|
||||
option_groups/index.rst
|
||||
kconfig/index.rst
|
||||
52
doc/services/portability/posix/kconfig/index.rst
Normal file
52
doc/services/portability/posix/kconfig/index.rst
Normal file
@@ -0,0 +1,52 @@
|
||||
.. _posix_kconfig_options:
|
||||
|
||||
Configuration Options
|
||||
*********************
|
||||
|
||||
This is a non-exhaustive list of specific :ref:`kconfig` options relating to Zephyr's
|
||||
implementation of the POSIX API.
|
||||
|
||||
* :kconfig:option:`CONFIG_APP_LINK_WITH_POSIX_SUBSYS`
|
||||
* :kconfig:option:`CONFIG_EVENTFD`
|
||||
* :kconfig:option:`CONFIG_EVENTFD_MAX`
|
||||
* :kconfig:option:`CONFIG_FDTABLE`
|
||||
* :kconfig:option:`CONFIG_FNMATCH`
|
||||
* :kconfig:option:`CONFIG_GETOPT`
|
||||
* :kconfig:option:`CONFIG_GETOPT_LONG`
|
||||
* :kconfig:option:`CONFIG_MAX_PTHREAD_BARRIER_COUNT`
|
||||
* :kconfig:option:`CONFIG_MAX_PTHREAD_COUNT`
|
||||
* :kconfig:option:`CONFIG_MAX_PTHREAD_KEY_COUNT`
|
||||
* :kconfig:option:`CONFIG_MAX_PTHREAD_MUTEX_COUNT`
|
||||
* :kconfig:option:`CONFIG_MAX_PTHREAD_SPINLOCK_COUNT`
|
||||
* :kconfig:option:`CONFIG_MAX_TIMER_COUNT`
|
||||
* :kconfig:option:`CONFIG_MQUEUE_NAMELEN_MAX`
|
||||
* :kconfig:option:`CONFIG_MSG_COUNT_MAX`
|
||||
* :kconfig:option:`CONFIG_MSG_SIZE_MAX`
|
||||
* :kconfig:option:`CONFIG_NET_SOCKETPAIR`
|
||||
* :kconfig:option:`CONFIG_NET_SOCKETS`
|
||||
* :kconfig:option:`CONFIG_NET_SOCKETS_POLL_MAX`
|
||||
* :kconfig:option:`CONFIG_NET_SOCKETS_POSIX_NAMES`
|
||||
* :kconfig:option:`CONFIG_POSIX_API`
|
||||
* :kconfig:option:`CONFIG_POSIX_CLOCK`
|
||||
* :kconfig:option:`CONFIG_POSIX_FS`
|
||||
* :kconfig:option:`CONFIG_POSIX_LIMITS_RTSIG_MAX`
|
||||
* :kconfig:option:`CONFIG_POSIX_MAX_FDS`
|
||||
* :kconfig:option:`CONFIG_POSIX_MAX_OPEN_FILES`
|
||||
* :kconfig:option:`CONFIG_POSIX_MQUEUE`
|
||||
* :kconfig:option:`CONFIG_POSIX_RTSIG_MAX`
|
||||
* :kconfig:option:`CONFIG_POSIX_SIGNAL`
|
||||
* :kconfig:option:`CONFIG_POSIX_SIGNAL_STRING_DESC`
|
||||
* :kconfig:option:`CONFIG_POSIX_UNAME`
|
||||
* :kconfig:option:`CONFIG_POSIX_UNAME_NODENAME_LEN`
|
||||
* :kconfig:option:`CONFIG_POSIX_UNAME_VERSION_LEN`
|
||||
* :kconfig:option:`CONFIG_PTHREAD`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_BARRIER`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_COND`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_CREATE_BARRIER`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_KEY`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_MUTEX`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_RECYCLER_DELAY_MS`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_SPINLOCK`
|
||||
* :kconfig:option:`CONFIG_SEM_VALUE_MAX`
|
||||
* :kconfig:option:`CONFIG_TIMER`
|
||||
@@ -1,131 +1,18 @@
|
||||
.. _posix_support:
|
||||
.. _posix_option_groups:
|
||||
|
||||
POSIX Support
|
||||
#############
|
||||
Subprofiling Option Groups
|
||||
##########################
|
||||
|
||||
The Portable Operating System Interface (POSIX) is a family of standards
|
||||
specified by the IEEE Computer Society for maintaining compatibility between
|
||||
operating systems. Zephyr implements a subset of the embedded profiles PSE51
|
||||
and PSE52, and BSD Sockets API.
|
||||
|
||||
With the POSIX support available in Zephyr, an existing POSIX compliant
|
||||
application can be ported to run on the Zephyr kernel, and therefore leverage
|
||||
Zephyr features and functionality. Additionally, a library designed for use with
|
||||
POSIX threading compatible operating systems can be ported to Zephyr kernel
|
||||
based applications with minimal or no changes.
|
||||
|
||||
.. figure:: posix.svg
|
||||
:align: center
|
||||
:alt: POSIX Support in Zephyr
|
||||
|
||||
POSIX support in Zephyr
|
||||
|
||||
The POSIX API subset is an increasingly popular OSAL (operating system
|
||||
abstraction layer) for IoT and embedded applications, as can be seen in
|
||||
Zephyr, AWS:FreeRTOS, TI-RTOS, and NuttX.
|
||||
|
||||
Benefits of POSIX support in Zephyr include:
|
||||
|
||||
- Offering a familiar API to non-embedded programmers, especially from Linux
|
||||
- Enabling reuse (portability) of existing libraries based on POSIX APIs
|
||||
- Providing an efficient API subset appropriate for small (MCU) embedded systems
|
||||
|
||||
|
||||
System Overview
|
||||
===============
|
||||
|
||||
Units of Functionality
|
||||
++++++++++++++++++++++
|
||||
|
||||
The system profile is defined in terms of component profiles that specify Units
|
||||
of Functionality that can be combined to realize the application platform. A Unit
|
||||
of Functionality is a defined set of services which can be implemented. If
|
||||
implemented, the standard prescribes that all services in the Unit must
|
||||
be implemented.
|
||||
|
||||
A Minimal Realtime System Profile implementation must support the
|
||||
following Units of Functionality as defined in IEEE Std. 1003.1 (also referred to
|
||||
as POSIX.1-2017).
|
||||
|
||||
|
||||
.. csv-table:: Units of Functionality
|
||||
:header: Requirements, Supported, Remarks
|
||||
:widths: 50,10,60
|
||||
|
||||
|
||||
POSIX_C_LANG_JUMP,
|
||||
POSIX_C_LANG_SUPPORT,yes
|
||||
POSIX_DEVICE_IO,
|
||||
POSIX_FILE_LOCKING,
|
||||
POSIX_SIGNALS,
|
||||
POSIX_SINGLE_PROCESS,
|
||||
POSIX_SPIN_LOCKS,yes
|
||||
POSIX_THREADS_BASE,yes
|
||||
XSI_THREAD_MUTEX_EXT,yes
|
||||
XSI_THREADS_EXT,yes
|
||||
|
||||
|
||||
Option Requirements
|
||||
++++++++++++++++++++
|
||||
|
||||
An implementation supporting the Minimal Realtime System
|
||||
Profile must support the POSIX.1 Option Requirements which are defined in the
|
||||
standard. Options Requirements are used for further sub-profiling within the
|
||||
units of functionality: they further define the functional behavior of the
|
||||
system service (normally adding extra functionality). Depending on the profile
|
||||
to which the POSIX implementation complies,parameters and/or the precise
|
||||
functionality of certain services may differ.
|
||||
|
||||
The following list shows the option requirements that are implemented in
|
||||
Zephyr.
|
||||
|
||||
|
||||
.. csv-table:: Option Requirements
|
||||
:header: Requirements, Supported
|
||||
:widths: 50,10
|
||||
|
||||
_POSIX_BARRIERS,yes
|
||||
_POSIX_CLOCK_SELECTION,yes
|
||||
_POSIX_FSYNC,
|
||||
_POSIX_MEMLOCK,
|
||||
_POSIX_MEMLOCK_RANGE,
|
||||
_POSIX_MONOTONIC_CLOCK,yes
|
||||
_POSIX_NO_TRUNC,
|
||||
_POSIX_REALTIME_SIGNALS,
|
||||
_POSIX_SEMAPHORES,yes
|
||||
_POSIX_SHARED_MEMORY_OBJECTS,
|
||||
_POSIX_SPIN_LOCKS,yes
|
||||
_POSIX_SYNCHRONIZED_IO,
|
||||
_POSIX_THREAD_ATTR_STACKADDR,yes
|
||||
_POSIX_THREAD_ATTR_STACKSIZE,yes
|
||||
_POSIX_THREAD_CPUTIME,
|
||||
_POSIX_THREAD_PRIO_INHERIT,
|
||||
_POSIX_THREAD_PRIO_PROTECT,
|
||||
_POSIX_THREAD_PRIORITY_SCHEDULING,yes
|
||||
_POSIX_THREAD_SPORADIC_SERVER,
|
||||
_POSIX_TIMEOUTS,
|
||||
_POSIX_TIMERS,yes
|
||||
_POSIX2_C_DEV,
|
||||
_POSIX2_SW_DEV,
|
||||
|
||||
|
||||
|
||||
Units of Functionality
|
||||
======================
|
||||
|
||||
This section describes the Units of Functionality (fixed sets of interfaces)
|
||||
which are implemented (partially or completely) in Zephyr. Please refer to the
|
||||
standard for a full description of each listed interface.
|
||||
.. _posix_option_group_threads_base:
|
||||
|
||||
POSIX_THREADS_BASE
|
||||
+++++++++++++++++++
|
||||
==================
|
||||
|
||||
The basic assumption in this profile is that the system
|
||||
consists of a single (implicit) process with multiple threads. Therefore, the
|
||||
standard requires all basic thread services, except those related to
|
||||
multiple processes.
|
||||
|
||||
|
||||
.. csv-table:: POSIX_THREADS_BASE
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
@@ -179,12 +66,12 @@ multiple processes.
|
||||
pthread_sigmask(),
|
||||
pthread_testcancel(),
|
||||
|
||||
|
||||
.. _posix_option_group_xsi_thread_ext:
|
||||
|
||||
XSI_THREAD_EXT
|
||||
++++++++++++++
|
||||
==============
|
||||
|
||||
The XSI_THREADS_EXT Unit of Functionality is required because it provides
|
||||
The XSI_THREADS_EXT option group is required because it provides
|
||||
functions to control a thread's stack. This is considered useful for any
|
||||
real-time application.
|
||||
|
||||
@@ -201,33 +88,14 @@ This table lists service support status in Zephyr:
|
||||
pthread_getconcurrency(),
|
||||
pthread_setconcurrency()
|
||||
|
||||
|
||||
XSI_THREAD_MUTEX_EXT
|
||||
++++++++++++++++++++
|
||||
|
||||
The XSI_THREAD_MUTEX_EXT Unit of Functionality is required because it has
|
||||
options for controlling the behavior of mutexes under erroneous application use.
|
||||
|
||||
|
||||
This table lists service support status in Zephyr:
|
||||
|
||||
.. csv-table:: XSI_THREAD_MUTEX_EXT
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_mutexattr_gettype(),yes
|
||||
pthread_mutexattr_settype(),yes
|
||||
|
||||
.. _posix_option_group_c_lang_support:
|
||||
|
||||
POSIX_C_LANG_SUPPORT
|
||||
++++++++++++++++++++
|
||||
====================
|
||||
|
||||
The POSIX_C_LANG_SUPPORT Unit of Functionality contains the general ISO C
|
||||
The POSIX_C_LANG_SUPPORT option group contains the general ISO C
|
||||
Library.
|
||||
|
||||
This is implemented as part of the minimal C library available in Zephyr.
|
||||
|
||||
|
||||
.. csv-table:: POSIX_C_LANG_SUPPORT
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
@@ -338,11 +206,12 @@ This is implemented as part of the minimal C library available in Zephyr.
|
||||
vsprintf(),yes
|
||||
vsscanf(),
|
||||
|
||||
.. _posix_option_group_single_process:
|
||||
|
||||
POSIX_SINGLE_PROCESS
|
||||
+++++++++++++++++++++
|
||||
====================
|
||||
|
||||
The POSIX_SINGLE_PROCESS Unit of Functionality contains services for single
|
||||
The POSIX_SINGLE_PROCESS option group contains services for single
|
||||
process applications.
|
||||
|
||||
.. csv-table:: POSIX_SINGLE_PROCESS
|
||||
@@ -358,9 +227,10 @@ process applications.
|
||||
uname(),yes
|
||||
unsetenv()
|
||||
|
||||
.. _posix_option_group_signals:
|
||||
|
||||
POSIX_SIGNALS
|
||||
+++++++++++++
|
||||
=============
|
||||
|
||||
Signal services are a basic mechanism within POSIX-based systems and are
|
||||
required for error and event handling.
|
||||
@@ -369,7 +239,6 @@ required for error and event handling.
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
|
||||
abort(),yes
|
||||
alarm(),
|
||||
kill(),
|
||||
@@ -388,32 +257,20 @@ required for error and event handling.
|
||||
sigwait(),
|
||||
strsignal(),yes
|
||||
|
||||
.. csv-table:: POSIX_SPIN_LOCKS
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_spin_destroy(),yes
|
||||
pthread_spin_init(),yes
|
||||
pthread_spin_lock(),yes
|
||||
pthread_spin_trylock(),yes
|
||||
pthread_spin_unlock(),yes
|
||||
|
||||
.. _posix_option_group_device_io:
|
||||
|
||||
POSIX_DEVICE_IO
|
||||
+++++++++++++++
|
||||
===============
|
||||
|
||||
.. csv-table:: POSIX_DEVICE_IO
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
flockfile(),
|
||||
ftrylockfile(),
|
||||
funlockfile(),
|
||||
getc_unlocked(),
|
||||
getchar_unlocked(),yes
|
||||
putc_unlocked(),
|
||||
putchar_unlocked()
|
||||
clearerr(),
|
||||
FD_CLR(),yes
|
||||
FD_ISSET(),yes
|
||||
FD_SET(),yes
|
||||
FD_ZERO(),yes
|
||||
clearerr(),yes
|
||||
close(),yes
|
||||
fclose(),
|
||||
fdopen(),
|
||||
@@ -436,17 +293,22 @@ POSIX_DEVICE_IO
|
||||
gets(),
|
||||
open(),yes
|
||||
perror(),yes
|
||||
poll(),yes
|
||||
printf(),yes
|
||||
pread(),
|
||||
pselect(),
|
||||
putc(),yes
|
||||
putchar(),yes
|
||||
puts(),yes
|
||||
pwrite(),
|
||||
read(),yes
|
||||
scanf(),
|
||||
select(),yes
|
||||
setbuf(),
|
||||
setvbuf(),
|
||||
stderr,yes
|
||||
stdin,yes
|
||||
stdout,yes
|
||||
stderr,
|
||||
stdin,
|
||||
stdout,
|
||||
ungetc(),
|
||||
vfprintf(),yes
|
||||
vfscanf(),
|
||||
@@ -454,8 +316,72 @@ POSIX_DEVICE_IO
|
||||
vscanf(),
|
||||
write(),yes
|
||||
|
||||
.. _posix_option_group_barriers:
|
||||
|
||||
POSIX_BARRIERS
|
||||
==============
|
||||
|
||||
.. csv-table:: POSIX_BARRIERS
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_barrier_destroy(),yes
|
||||
pthread_barrier_init(),yes
|
||||
pthread_barrier_wait(),yes
|
||||
pthread_barrierattr_destroy(),yes
|
||||
pthread_barrierattr_init(),yes
|
||||
|
||||
.. _posix_option_group_clock_selection:
|
||||
|
||||
POSIX_CLOCK_SELECTION
|
||||
=====================
|
||||
|
||||
.. csv-table:: POSIX_CLOCK_SELECTION
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_condattr_getclock(),yes
|
||||
pthread_condattr_setclock(),yes
|
||||
clock_nanosleep(),yes
|
||||
|
||||
.. _posix_option_group_semaphores:
|
||||
|
||||
POSIX_SEMAPHORES
|
||||
================
|
||||
|
||||
.. csv-table:: POSIX_SEMAPHORES
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
sem_close(),
|
||||
sem_destroy(),yes
|
||||
sem_getvalue(),yes
|
||||
sem_init(),yes
|
||||
sem_open(),
|
||||
sem_post(),yes
|
||||
sem_trywait(),yes
|
||||
sem_unlink(),
|
||||
sem_wait(),yes
|
||||
|
||||
.. _posix_option_group_spin_locks:
|
||||
|
||||
POSIX_SPIN_LOCKS
|
||||
================
|
||||
|
||||
.. csv-table:: POSIX_SPIN_LOCKS
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_spin_destroy(),yes
|
||||
pthread_spin_init(),yes
|
||||
pthread_spin_lock(),yes
|
||||
pthread_spin_trylock(),yes
|
||||
pthread_spin_unlock(),yes
|
||||
|
||||
.. _posix_option_group_timers:
|
||||
|
||||
POSIX_TIMERS
|
||||
++++++++++++
|
||||
============
|
||||
|
||||
.. csv-table:: POSIX_TIMERS
|
||||
:header: API, Supported
|
||||
@@ -471,13 +397,143 @@ POSIX_TIMERS
|
||||
timer_getoverrun(),yes
|
||||
timer_settime(),yes
|
||||
|
||||
POSIX_CLOCK_SELECTION
|
||||
+++++++++++++++++++++
|
||||
|
||||
.. csv-table:: POSIX_CLOCK_SELECTION
|
||||
.. _posix_options:
|
||||
|
||||
Additional POSIX Options
|
||||
========================
|
||||
|
||||
.. _posix_option_message_passing:
|
||||
|
||||
_POSIX_MESSAGE_PASSING
|
||||
++++++++++++++++++++++
|
||||
|
||||
.. csv-table:: _POSIX_MESSAGE_PASSING
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_condattr_getclock(),yes
|
||||
pthread_condattr_setclock(),yes
|
||||
clock_nanosleep(),yes
|
||||
mq_close(),yes
|
||||
mq_getattr(),yes
|
||||
mq_notify(),
|
||||
mq_open(),yes
|
||||
mq_receive(),yes
|
||||
mq_send(),yes
|
||||
mq_setattr(),yes
|
||||
mq_unlink(),yes
|
||||
|
||||
_POSIX_PRIORITY_SCHEDULING
|
||||
++++++++++++++++++++++++++
|
||||
|
||||
.. _posix_option_priority_scheduling:
|
||||
|
||||
.. csv-table:: _POSIX_PRIORITY_SCHEDULING
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
sched_get_priority_max(),yes
|
||||
sched_get_priority_min(),yes
|
||||
sched_getparam(),
|
||||
sched_getscheduler(),
|
||||
sched_rr_get_interval(),
|
||||
sched_setparam(),
|
||||
sched_setscheduler(),
|
||||
sched_yield(),yes
|
||||
|
||||
.. _posix_option_reader_writer_locks:
|
||||
|
||||
_POSIX_READER_WRITER_LOCKS
|
||||
++++++++++++++++++++++++++
|
||||
|
||||
.. csv-table:: _POSIX_READER_WRITER_LOCKS
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_rwlock_destroy(),yes
|
||||
pthread_rwlock_init(),yes
|
||||
pthread_rwlock_rdlock(),yes
|
||||
pthread_rwlock_tryrdlock(),yes
|
||||
pthread_rwlock_trywrlock(),yes
|
||||
pthread_rwlock_unlock(),yes
|
||||
pthread_rwlock_wrlock(),yes
|
||||
pthread_rwlockattr_destroy(),yes
|
||||
pthread_rwlockattr_getpshared(),
|
||||
pthread_rwlockattr_init(),yes
|
||||
pthread_rwlockattr_setpshared(),
|
||||
|
||||
.. _posix_option_thread_attr_stackaddr:
|
||||
|
||||
_POSIX_THREAD_ATTR_STACKADDR
|
||||
++++++++++++++++++++++++++++
|
||||
|
||||
.. csv-table:: _POSIX_THREAD_ATTR_STACKADDR
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_attr_getstackaddr(),yes
|
||||
pthread_attr_setstackaddr(),yes
|
||||
|
||||
.. _posix_option_thread_attr_stacksize:
|
||||
|
||||
_POSIX_THREAD_ATTR_STACKSIZE
|
||||
++++++++++++++++++++++++++++
|
||||
|
||||
.. csv-table:: _POSIX_THREAD_ATTR_STACKSIZE
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_attr_getstacksize(),yes
|
||||
pthread_attr_setstacksize(),yes
|
||||
|
||||
.. _posix_option_thread_priority_scheduling:
|
||||
|
||||
_POSIX_THREAD_PRIORITY_SCHEDULING
|
||||
+++++++++++++++++++++++++++++++++
|
||||
|
||||
.. csv-table:: _POSIX_THREAD_PRIORITY_SCHEDULING
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
pthread_attr_getinheritsched(),
|
||||
pthread_attr_getschedpolicy(),yes
|
||||
pthread_attr_getscope(),
|
||||
pthread_attr_setinheritsched(),
|
||||
pthread_attr_setschedpolicy(),yes
|
||||
pthread_attr_setscope(),
|
||||
pthread_getschedparam(),yes
|
||||
pthread_setschedparam(),yes
|
||||
pthread_setschedprio(),yes
|
||||
|
||||
.. _posix_option_timeouts:
|
||||
|
||||
_POSIX_TIMEOUTS
|
||||
+++++++++++++++
|
||||
|
||||
.. csv-table:: _POSIX_TIMEOUTS
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
mq_timedreceive(),
|
||||
mq_timedsend(),
|
||||
pthread_mutex_timedlock(),yes
|
||||
pthread_rwlock_timedrdlock(),yes
|
||||
pthread_rwlock_timedwrlock(),yes
|
||||
sem_timedwait(),yes
|
||||
posix_trace_timedgetnext_event(),
|
||||
|
||||
.. _posix_option_xopen_streams:
|
||||
|
||||
_XOPEN_STREAMS
|
||||
++++++++++++++
|
||||
|
||||
.. csv-table:: _XOPEN_STREAMS
|
||||
:header: API, Supported
|
||||
:widths: 50,10
|
||||
|
||||
fattach(),
|
||||
fdetach(),
|
||||
getmsg(),
|
||||
getpmsg(),
|
||||
ioctl(),yes
|
||||
isastream(),
|
||||
putmsg(),
|
||||
putpmsg(),
|
||||
135
doc/services/portability/posix/overview/index.rst
Normal file
135
doc/services/portability/posix/overview/index.rst
Normal file
@@ -0,0 +1,135 @@
|
||||
.. _posix_overview:
|
||||
|
||||
Overview
|
||||
########
|
||||
|
||||
The Portable Operating System Interface (POSIX) is a family of standards specified by the
|
||||
`IEEE Computer Society`_ for maintaining compatibility between operating systems. Zephyr
|
||||
implements a subset of the standard POSIX API specified by `IEEE 1003.1-2017`_ (also known as
|
||||
POSIX-1.2017).
|
||||
|
||||
.. figure:: posix.svg
|
||||
:align: center
|
||||
:alt: POSIX Support in Zephyr
|
||||
|
||||
POSIX support in Zephyr
|
||||
|
||||
.. note::
|
||||
This page does not document Zephyr's :ref:`POSIX architecture<Posix arch>`, which is used to
|
||||
run Zephyr as a native application under the host operating system for prototyping,
|
||||
test, and diagnostic purposes.
|
||||
|
||||
With the POSIX support available in Zephyr, an existing POSIX conformant
|
||||
application can be ported to run on the Zephyr kernel, and therefore leverage
|
||||
Zephyr features and functionality. Additionally, a library designed to be
|
||||
POSIX conformant can be ported to Zephyr kernel based applications with no changes.
|
||||
|
||||
The POSIX API is an increasingly popular OSAL (operating system abstraction layer) for IoT and
|
||||
embedded applications, as can be seen in Zephyr, AWS:FreeRTOS, TI-RTOS, and NuttX.
|
||||
|
||||
Benefits of POSIX support in Zephyr include:
|
||||
|
||||
- Offering a familiar API to non-embedded programmers, especially from Linux
|
||||
- Enabling reuse (portability) of existing libraries based on POSIX APIs
|
||||
- Providing an efficient API subset appropriate for small (MCU) embedded systems
|
||||
|
||||
.. _posix_subprofiles:
|
||||
|
||||
POSIX Subprofiles
|
||||
=================
|
||||
|
||||
While Zephyr supports running multiple `threads <threads_v2>`_ (possibly in an `SMP <smp_arch>`_
|
||||
configuration), as well as `Virtual Memory and MMUs <memory_management_api>`_, Zephyr code and data
|
||||
normally share a common address space. The Zephyr kernel executable code and the application
|
||||
executable code are typically compiled into the same binary artifact. From that perspective, Zephyr
|
||||
apps can be seen as running in the context of a single process.
|
||||
|
||||
While multi-purpose operating systems (OS) offer full POSIX conformance, Real-Time Operating
|
||||
Systems (RTOS) such as Zephyr typically serve a fixed-purpose, have limited hardware resources,
|
||||
and experience limited user interaction. In such systems, full POSIX conformance can be
|
||||
impractical and unnecessary.
|
||||
|
||||
For that reason, POSIX defined the following :ref:`Application Environment Profiles (AEP)<posix_aep>`
|
||||
as part of `IEEE 1003.13-2003`_ (also known as POSIX.13-2003).
|
||||
|
||||
* Minimal Realtime System Profile (:ref:`PSE51 <posix_aep_pse51>`)
|
||||
* Realtime Controller System Profile (:ref:`PSE52 <posix_aep_pse52>`)
|
||||
* Dedicated Realtime System Profile (:ref:`PSE53 <posix_aep_pse53>`)
|
||||
* Multi-Purpose Realtime System (PSE54)
|
||||
|
||||
POSIX.13-2003 AEP were formalized in 2003 via "Units of Functionality" but the specification is now
|
||||
inactive (for reference only). Nevertheless, the intent is still captured as part of POSIX-1.2017
|
||||
via :ref:`Options<posix_options>` and :ref:`Option Groups<posix_option_groups>`, in Appendix E.
|
||||
|
||||
.. _posix_apps:
|
||||
|
||||
POSIX Applications in Zephyr
|
||||
============================
|
||||
|
||||
A POSIX app in Zephyr is :ref:`built like any other app<application>` and therefore requires the
|
||||
usual :file:`prj.conf`, :file:`CMakeLists.txt`, and source code. For example, the app below
|
||||
leverages the ``nanosleep()`` and ``perror()`` POSIX functions.
|
||||
|
||||
.. code-block:: cfg
|
||||
:caption: `prj.conf` for a simple POSIX app in Zephyr
|
||||
|
||||
CONFIG_POSIX_API=y
|
||||
|
||||
.. code-block:: c
|
||||
:caption: A simple app that uses Zephyr's POSIX API
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdio.h>
|
||||
#include <time.h>
|
||||
|
||||
void megasleep(size_t megaseconds)
|
||||
{
|
||||
struct timespec ts = {
|
||||
.tv_sec = megaseconds * 1000000,
|
||||
.tv_nsec = 0,
|
||||
};
|
||||
|
||||
printf("See you in a while!\n");
|
||||
if (nanosleep(&ts, NULL) == -1) {
|
||||
perror("nanosleep");
|
||||
}
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
megasleep(42);
|
||||
return 0;
|
||||
}
|
||||
|
||||
..
|
||||
TODO: insert a link to a list of all samples tagged with 'posix'
|
||||
|
||||
.. _posix_config:
|
||||
|
||||
Configuration
|
||||
=============
|
||||
|
||||
Like most features in Zephyr, POSIX features are
|
||||
:ref:`highly configurable<zephyr_intro_configurability>` but disabled by default. Users must
|
||||
explicitly choose to enable POSIX options via :ref:`Kconfig<kconfig>` selection. Indeed, there are
|
||||
:ref:`many Kconfig options in Zephyr<posix_kconfig_options>` for the POSIX API to allow for
|
||||
feature selection at various levels of granularity.
|
||||
|
||||
Alternatively, users may enable one of the Kconfig options below as a shortcut to enable multiple
|
||||
:ref:`Option Groups<posix_option_groups>`.
|
||||
|
||||
* :kconfig:option:`CONFIG_POSIX_API`
|
||||
* :kconfig:option:`CONFIG_PTHREAD_IPC`
|
||||
|
||||
.. note::
|
||||
Since the POSIX environment in Zephyr is fully configurable via :ref:`Kconfig<kconfig>`,
|
||||
configurations that require modifying features should not be made if strict compliance is
|
||||
required (POSIX-1.2017, section 2.1.3.1).
|
||||
|
||||
..
|
||||
TODO: create Kconfig shortcuts for PSE51, PSE52, and PSE53
|
||||
|
||||
.. _IEEE: https://www.ieee.org/
|
||||
.. _IEEE Computer Society: https://www.computer.org/
|
||||
.. _IEEE 1003.1-2017: https://standards.ieee.org/ieee/1003.1/7101/
|
||||
.. _IEEE 1003.13-2003: https://standards.ieee.org/ieee/1003.13/3322/
|
||||
File diff suppressed because one or more lines are too long
|
Before Width: | Height: | Size: 10 KiB After Width: | Height: | Size: 9.9 KiB |
File diff suppressed because one or more lines are too long
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
@@ -235,17 +235,22 @@ priority.
|
||||
it cannot access the channel since it is still locked.
|
||||
|
||||
* - i
|
||||
- VDED finishes the publishing by unlocking channel A.
|
||||
- VDED finishes the publishing by unlocking channel A. The MS1 leaves the pending state and
|
||||
starts executing.
|
||||
|
||||
* - j, k, l
|
||||
* - j
|
||||
- MS1 finishes execution. The MS2 leaves the pending state and starts executing.
|
||||
|
||||
* - k
|
||||
- MS2 finishes execution. The S1 leaves the pending state and starts executing.
|
||||
|
||||
* - l, m, n
|
||||
- The S1 leaves the pending state since channel A is not locked. It gets in the CPU again and
|
||||
starts executing. As it did receive a notification from channel A, it performs a channel read
|
||||
(as simple as lock, memory copy, unlock), continues its execution, and goes out the CPU.
|
||||
* - m
|
||||
- S1 goes out of the MCU.
|
||||
starts executing. As it did receive a notification from channel A, it performed a channel read
|
||||
(as simple as lock, memory copy, unlock), continues its execution and goes out of the CPU.
|
||||
|
||||
* - n, o
|
||||
- MS2 and MS1 execute and finish their workload.
|
||||
* - o
|
||||
- S1 finishes its workload.
|
||||
|
||||
|
||||
The figure below illustrates the actions performed during the VDED execution when T1 publishes to
|
||||
|
||||
@@ -639,7 +639,7 @@ static int lmp90xxx_adc_read_channel(const struct device *dev,
|
||||
if (buf[3] != crc) {
|
||||
LOG_ERR("CRC mismatch (0x%02x vs. 0x%02x)", buf[3],
|
||||
crc);
|
||||
return err;
|
||||
return -EIO;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1007,8 +1007,6 @@ static void adc_context_on_complete(struct adc_context *ctx, int status)
|
||||
|
||||
ARG_UNUSED(status);
|
||||
|
||||
adc_stm32_disable(adc);
|
||||
|
||||
/* Reset acquisition time used for the sequence */
|
||||
data->acq_time_index = -1;
|
||||
|
||||
@@ -1019,6 +1017,8 @@ static void adc_context_on_complete(struct adc_context *ctx, int status)
|
||||
#if defined(CONFIG_SOC_SERIES_STM32H7X) || defined(CONFIG_SOC_SERIES_STM32U5X)
|
||||
/* Reset channel preselection register */
|
||||
LL_ADC_SetChannelPreselection(adc, 0);
|
||||
#else
|
||||
ARG_UNUSED(adc);
|
||||
#endif /* CONFIG_SOC_SERIES_STM32H7X || CONFIG_SOC_SERIES_STM32U5X */
|
||||
}
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
# Bosch m_can configuration options
|
||||
# Bosch M_CAN configuration options
|
||||
|
||||
# Copyright (c) 2020 Alexander Wachter
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
@@ -6,17 +6,4 @@
|
||||
config CAN_MCAN
|
||||
bool
|
||||
help
|
||||
Enable Bosch m_can driver.
|
||||
This driver supports the Bosch m_can IP. This IP is built into the
|
||||
STM32G4, STM32G0, STM32H7, and the Microchip SAM controllers with
|
||||
CAN-FD.
|
||||
|
||||
if CAN_MCAN
|
||||
|
||||
config CAN_DELAY_COMP
|
||||
bool "Transceiver delay compensation"
|
||||
default y
|
||||
help
|
||||
Enable the automatic transceiver delay compensation.
|
||||
|
||||
endif #CAN_MCAN
|
||||
Enable the Bosch M_CAN CAN IP module driver backend.
|
||||
|
||||
@@ -211,7 +211,7 @@ static void can_loopback_remove_rx_filter(const struct device *dev, int filter_i
|
||||
{
|
||||
struct can_loopback_data *data = dev->data;
|
||||
|
||||
if (filter_id >= ARRAY_SIZE(data->filters)) {
|
||||
if (filter_id < 0 || filter_id >= ARRAY_SIZE(data->filters)) {
|
||||
LOG_ERR("filter ID %d out-of-bounds", filter_id);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -225,8 +225,10 @@ unlock:
|
||||
#ifdef CONFIG_CAN_FD_MODE
|
||||
int can_mcan_set_timing_data(const struct device *dev, const struct can_timing *timing_data)
|
||||
{
|
||||
const uint8_t tdco_max = FIELD_GET(CAN_MCAN_TDCR_TDCO, CAN_MCAN_TDCR_TDCO);
|
||||
struct can_mcan_data *data = dev->data;
|
||||
uint32_t dbtp = 0U;
|
||||
uint8_t tdco;
|
||||
int err;
|
||||
|
||||
if (data->started) {
|
||||
@@ -240,6 +242,23 @@ int can_mcan_set_timing_data(const struct device *dev, const struct can_timing *
|
||||
FIELD_PREP(CAN_MCAN_DBTP_DTSEG2, timing_data->phase_seg2 - 1UL) |
|
||||
FIELD_PREP(CAN_MCAN_DBTP_DBRP, timing_data->prescaler - 1UL);
|
||||
|
||||
if (timing_data->prescaler == 1U || timing_data->prescaler == 2U) {
|
||||
/* TDC can only be enabled if DBRP = { 0, 1 } */
|
||||
dbtp |= CAN_MCAN_DBTP_TDC;
|
||||
|
||||
/* Set TDC offset for correct location of the Secondary Sample Point (SSP) */
|
||||
tdco = CAN_CALC_TDCO(timing_data, 0U, tdco_max);
|
||||
LOG_DBG("TDC enabled, using TDCO %u", tdco);
|
||||
|
||||
err = can_mcan_write_reg(dev, CAN_MCAN_TDCR, FIELD_PREP(CAN_MCAN_TDCR_TDCO, tdco));
|
||||
if (err != 0) {
|
||||
goto unlock;
|
||||
}
|
||||
} else {
|
||||
LOG_DBG("TDC cannot be enabled, prescaler value %u too high",
|
||||
timing_data->prescaler);
|
||||
}
|
||||
|
||||
err = can_mcan_write_reg(dev, CAN_MCAN_DBTP, dbtp);
|
||||
if (err != 0) {
|
||||
goto unlock;
|
||||
@@ -426,16 +445,59 @@ unlock:
|
||||
|
||||
static void can_mcan_state_change_handler(const struct device *dev)
|
||||
{
|
||||
const struct can_mcan_config *config = dev->config;
|
||||
struct can_mcan_data *data = dev->data;
|
||||
const can_state_change_callback_t cb = data->state_change_cb;
|
||||
void *cb_data = data->state_change_cb_data;
|
||||
const can_state_change_callback_t state_cb = data->state_change_cb;
|
||||
void *state_cb_data = data->state_change_cb_data;
|
||||
const struct can_mcan_callbacks *cbs = config->callbacks;
|
||||
can_tx_callback_t tx_cb;
|
||||
uint32_t tx_idx;
|
||||
struct can_bus_err_cnt err_cnt;
|
||||
enum can_state state;
|
||||
uint32_t cccr;
|
||||
int err;
|
||||
|
||||
(void)can_mcan_get_state(dev, &state, &err_cnt);
|
||||
|
||||
if (cb != NULL) {
|
||||
cb(dev, state, err_cnt, cb_data);
|
||||
if (state_cb != NULL) {
|
||||
state_cb(dev, state, err_cnt, state_cb_data);
|
||||
}
|
||||
|
||||
if (state == CAN_STATE_BUS_OFF) {
|
||||
/* Request all TX buffers to be cancelled */
|
||||
err = can_mcan_write_reg(dev, CAN_MCAN_TXBCR, CAN_MCAN_TXBCR_CR);
|
||||
if (err != 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
/* Call all TX queue callbacks with -ENETUNREACH */
|
||||
for (tx_idx = 0U; tx_idx < cbs->num_tx; tx_idx++) {
|
||||
tx_cb = cbs->tx[tx_idx].function;
|
||||
|
||||
if (tx_cb != NULL) {
|
||||
cbs->tx[tx_idx].function = NULL;
|
||||
tx_cb(dev, -ENETUNREACH, cbs->tx[tx_idx].user_data);
|
||||
k_sem_give(&data->tx_sem);
|
||||
}
|
||||
}
|
||||
|
||||
if (IS_ENABLED(CONFIG_CAN_AUTO_BUS_OFF_RECOVERY)) {
|
||||
/*
|
||||
* Request leaving init mode, but do not take the lock (as we are in ISR
|
||||
* context), nor wait for the result.
|
||||
*/
|
||||
err = can_mcan_read_reg(dev, CAN_MCAN_CCCR, &cccr);
|
||||
if (err != 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
cccr &= ~CAN_MCAN_CCCR_INIT;
|
||||
|
||||
err = can_mcan_write_reg(dev, CAN_MCAN_CCCR, cccr);
|
||||
if (err != 0) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1149,12 +1211,17 @@ void can_mcan_remove_rx_filter(const struct device *dev, int filter_id)
|
||||
struct can_mcan_data *data = dev->data;
|
||||
int err;
|
||||
|
||||
if (filter_id < 0) {
|
||||
LOG_ERR("filter ID %d out of bounds", filter_id);
|
||||
return;
|
||||
}
|
||||
|
||||
k_mutex_lock(&data->lock, K_FOREVER);
|
||||
|
||||
if (filter_id >= cbs->num_std) {
|
||||
filter_id -= cbs->num_std;
|
||||
if (filter_id >= cbs->num_ext) {
|
||||
LOG_ERR("Wrong filter id");
|
||||
LOG_ERR("filter ID %d out of bounds", filter_id);
|
||||
k_mutex_unlock(&data->lock);
|
||||
return;
|
||||
}
|
||||
@@ -1407,32 +1474,6 @@ int can_mcan_init(const struct device *dev)
|
||||
return err;
|
||||
}
|
||||
|
||||
#if defined(CONFIG_CAN_DELAY_COMP) && defined(CONFIG_CAN_FD_MODE)
|
||||
err = can_mcan_read_reg(dev, CAN_MCAN_DBTP, ®);
|
||||
if (err != 0) {
|
||||
return err;
|
||||
}
|
||||
|
||||
reg |= CAN_MCAN_DBTP_TDC;
|
||||
|
||||
err = can_mcan_write_reg(dev, CAN_MCAN_DBTP, reg);
|
||||
if (err != 0) {
|
||||
return err;
|
||||
}
|
||||
|
||||
err = can_mcan_read_reg(dev, CAN_MCAN_TDCR, ®);
|
||||
if (err != 0) {
|
||||
return err;
|
||||
}
|
||||
|
||||
reg |= FIELD_PREP(CAN_MCAN_TDCR_TDCO, config->tx_delay_comp_offset);
|
||||
|
||||
err = can_mcan_write_reg(dev, CAN_MCAN_TDCR, reg);
|
||||
if (err != 0) {
|
||||
return err;
|
||||
}
|
||||
#endif /* defined(CONFIG_CAN_DELAY_COMP) && defined(CONFIG_CAN_FD_MODE) */
|
||||
|
||||
err = can_mcan_read_reg(dev, CAN_MCAN_GFC, ®);
|
||||
if (err != 0) {
|
||||
return err;
|
||||
@@ -1527,7 +1568,7 @@ int can_mcan_init(const struct device *dev)
|
||||
return err;
|
||||
}
|
||||
|
||||
/* Interrupt on every TX fifo element*/
|
||||
/* Interrupt on every TX buffer transmission event */
|
||||
reg = CAN_MCAN_TXBTIE_TIE;
|
||||
err = can_mcan_write_reg(dev, CAN_MCAN_TXBTIE, reg);
|
||||
if (err != 0) {
|
||||
|
||||
@@ -661,6 +661,11 @@ static void mcp2515_remove_rx_filter(const struct device *dev, int filter_id)
|
||||
{
|
||||
struct mcp2515_data *dev_data = dev->data;
|
||||
|
||||
if (filter_id < 0 || filter_id >= CONFIG_CAN_MAX_FILTER) {
|
||||
LOG_ERR("filter ID %d out of bounds", filter_id);
|
||||
return;
|
||||
}
|
||||
|
||||
k_mutex_lock(&dev_data->mutex, K_FOREVER);
|
||||
dev_data->filter_usage &= ~BIT(filter_id);
|
||||
k_mutex_unlock(&dev_data->mutex);
|
||||
|
||||
@@ -922,9 +922,8 @@ static void mcux_flexcan_remove_rx_filter(const struct device *dev, int filter_i
|
||||
{
|
||||
struct mcux_flexcan_data *data = dev->data;
|
||||
|
||||
if (filter_id >= MCUX_FLEXCAN_MAX_RX) {
|
||||
LOG_ERR("Detach: Filter id >= MAX_RX (%d >= %d)", filter_id,
|
||||
MCUX_FLEXCAN_MAX_RX);
|
||||
if (filter_id < 0 || filter_id >= MCUX_FLEXCAN_MAX_RX) {
|
||||
LOG_ERR("filter ID %d out of bounds", filter_id);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -239,6 +239,7 @@ static void can_npl_remove_rx_filter(const struct device *dev, int filter_id)
|
||||
struct can_npl_data *data = dev->data;
|
||||
|
||||
if (filter_id < 0 || filter_id >= ARRAY_SIZE(data->filters)) {
|
||||
LOG_ERR("filter ID %d out of bounds");
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -396,7 +396,10 @@ static void can_nxp_s32_remove_rx_filter(const struct device *dev, int filter_id
|
||||
struct can_nxp_s32_data *data = dev->data;
|
||||
int mb_indx = ALLOC_IDX_TO_RXMB_IDX(filter_id);
|
||||
|
||||
__ASSERT_NO_MSG(filter_id >= 0 && filter_id < CONFIG_CAN_NXP_S32_MAX_RX);
|
||||
if (filter_id < 0 || filter_id >= CONFIG_CAN_NXP_S32_MAX_RX) {
|
||||
LOG_ERR("filter ID %d out of bounds", filter_id);
|
||||
return;
|
||||
}
|
||||
|
||||
k_mutex_lock(&data->rx_mutex, K_FOREVER);
|
||||
|
||||
|
||||
@@ -975,7 +975,8 @@ static void can_rcar_remove_rx_filter(const struct device *dev, int filter_id)
|
||||
{
|
||||
struct can_rcar_data *data = dev->data;
|
||||
|
||||
if (filter_id >= CONFIG_CAN_RCAR_MAX_FILTER) {
|
||||
if (filter_id < 0 || filter_id >= CONFIG_CAN_RCAR_MAX_FILTER) {
|
||||
LOG_ERR("filter ID %d out of bounds", filter_id);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -560,7 +560,7 @@ static int cmd_can_send(const struct shell *sh, size_t argc, char **argv)
|
||||
const struct device *dev = device_get_binding(argv[1]);
|
||||
static unsigned int frame_counter;
|
||||
unsigned int frame_no;
|
||||
struct can_frame frame;
|
||||
struct can_frame frame = { 0 };
|
||||
uint32_t max_id;
|
||||
int argidx = 2;
|
||||
uint32_t val;
|
||||
@@ -665,7 +665,7 @@ static int cmd_can_send(const struct shell *sh, size_t argc, char **argv)
|
||||
(frame.flags & CAN_FRAME_RTR) != 0 ? 1 : 0,
|
||||
(frame.flags & CAN_FRAME_FDF) != 0 ? 1 : 0,
|
||||
(frame.flags & CAN_FRAME_BRS) != 0 ? 1 : 0,
|
||||
can_dlc_to_bytes(frame.dlc));
|
||||
frame.dlc);
|
||||
|
||||
err = can_send(dev, &frame, K_NO_WAIT, can_shell_tx_callback, UINT_TO_POINTER(frame_no));
|
||||
if (err != 0) {
|
||||
|
||||
@@ -1035,7 +1035,10 @@ static void can_stm32_remove_rx_filter(const struct device *dev, int filter_id)
|
||||
int bank_num;
|
||||
bool bank_unused;
|
||||
|
||||
__ASSERT_NO_MSG(filter_id >= 0 && filter_id < CAN_STM32_MAX_FILTER_ID);
|
||||
if (filter_id < 0 || filter_id >= CAN_STM32_MAX_FILTER_ID) {
|
||||
LOG_ERR("filter ID %d out of bounds", filter_id);
|
||||
return;
|
||||
}
|
||||
|
||||
k_mutex_lock(&filter_mutex, K_FOREVER);
|
||||
k_mutex_lock(&data->inst_mutex, K_FOREVER);
|
||||
|
||||
@@ -297,14 +297,15 @@ int eth_ivshmem_initialize(const struct device *dev)
|
||||
}
|
||||
dev_data->peer_id = (id == 0) ? 1 : 0;
|
||||
|
||||
bool tx_buffer_first = id == 0;
|
||||
uintptr_t output_section_addr;
|
||||
uintptr_t output_sections[2];
|
||||
size_t output_section_size = ivshmem_get_output_mem_section(
|
||||
cfg_data->ivshmem, 0, &output_section_addr);
|
||||
cfg_data->ivshmem, 0, &output_sections[0]);
|
||||
ivshmem_get_output_mem_section(
|
||||
cfg_data->ivshmem, 1, &output_sections[1]);
|
||||
|
||||
res = eth_ivshmem_queue_init(
|
||||
&dev_data->ivshmem_queue, output_section_addr,
|
||||
output_section_size, tx_buffer_first);
|
||||
&dev_data->ivshmem_queue, output_sections[id],
|
||||
output_sections[dev_data->peer_id], output_section_size);
|
||||
if (res != 0) {
|
||||
LOG_ERR("Failed to init ivshmem queue");
|
||||
return res;
|
||||
|
||||
@@ -40,8 +40,8 @@ struct eth_ivshmem_queue {
|
||||
};
|
||||
|
||||
int eth_ivshmem_queue_init(
|
||||
struct eth_ivshmem_queue *q, uintptr_t shmem,
|
||||
size_t shmem_section_size, bool tx_buffer_first);
|
||||
struct eth_ivshmem_queue *q, uintptr_t tx_shmem,
|
||||
uintptr_t rx_shmem, size_t shmem_section_size);
|
||||
void eth_ivshmem_queue_reset(struct eth_ivshmem_queue *q);
|
||||
int eth_ivshmem_queue_tx_get_buff(struct eth_ivshmem_queue *q, void **data, size_t len);
|
||||
int eth_ivshmem_queue_tx_commit_buff(struct eth_ivshmem_queue *q);
|
||||
|
||||
@@ -28,8 +28,8 @@ static int tx_clean_used(struct eth_ivshmem_queue *q);
|
||||
static int get_rx_avail_desc_idx(struct eth_ivshmem_queue *q, uint16_t *avail_desc_idx);
|
||||
|
||||
int eth_ivshmem_queue_init(
|
||||
struct eth_ivshmem_queue *q, uintptr_t shmem,
|
||||
size_t shmem_section_size, bool tx_buffer_first)
|
||||
struct eth_ivshmem_queue *q, uintptr_t tx_shmem,
|
||||
uintptr_t rx_shmem, size_t shmem_section_size)
|
||||
{
|
||||
memset(q, 0, sizeof(*q));
|
||||
|
||||
@@ -44,14 +44,8 @@ int eth_ivshmem_queue_init(
|
||||
q->desc_max_len = vring_desc_len;
|
||||
q->vring_data_max_len = shmem_section_size - vring_header_size;
|
||||
q->vring_header_size = vring_header_size;
|
||||
|
||||
if (tx_buffer_first) {
|
||||
q->tx.shmem = (void *)shmem;
|
||||
q->rx.shmem = (void *)(shmem + shmem_section_size);
|
||||
} else {
|
||||
q->rx.shmem = (void *)shmem;
|
||||
q->tx.shmem = (void *)(shmem + shmem_section_size);
|
||||
}
|
||||
q->tx.shmem = (void *)tx_shmem;
|
||||
q->rx.shmem = (void *)rx_shmem;
|
||||
|
||||
/* Init vrings */
|
||||
vring_init(&q->tx.vring, vring_desc_len, q->tx.shmem, ETH_IVSHMEM_VRING_ALIGNMENT);
|
||||
|
||||
@@ -58,9 +58,17 @@ enum {
|
||||
ERASE_CHIP,
|
||||
};
|
||||
|
||||
struct flash_flexspi_nor_config {
|
||||
/* Note: don't use this controller reference in code. It is
|
||||
* only used during init to copy the device structure from ROM
|
||||
* into a RAM structure
|
||||
*/
|
||||
const struct device *controller;
|
||||
};
|
||||
|
||||
/* Device variables used in critical sections should be in this structure */
|
||||
struct flash_flexspi_nor_data {
|
||||
const struct device *controller;
|
||||
struct device controller;
|
||||
flexspi_device_config_t config;
|
||||
flexspi_port_t port;
|
||||
struct flash_pages_layout layout;
|
||||
@@ -154,10 +162,9 @@ static const uint32_t flash_flexspi_nor_lut[][4] = {
|
||||
},
|
||||
};
|
||||
|
||||
static int flash_flexspi_nor_get_vendor_id(const struct device *dev,
|
||||
static int flash_flexspi_nor_get_vendor_id(struct flash_flexspi_nor_data *data,
|
||||
uint8_t *vendor_id)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
uint32_t buffer = 0;
|
||||
int ret;
|
||||
|
||||
@@ -173,17 +180,15 @@ static int flash_flexspi_nor_get_vendor_id(const struct device *dev,
|
||||
|
||||
LOG_DBG("Reading id");
|
||||
|
||||
ret = memc_flexspi_transfer(data->controller, &transfer);
|
||||
ret = memc_flexspi_transfer(&data->controller, &transfer);
|
||||
*vendor_id = buffer;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_read_status(const struct device *dev,
|
||||
static int flash_flexspi_nor_read_status(struct flash_flexspi_nor_data *data,
|
||||
uint32_t *status)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
|
||||
flexspi_transfer_t transfer = {
|
||||
.deviceAddress = 0,
|
||||
.port = data->port,
|
||||
@@ -196,14 +201,12 @@ static int flash_flexspi_nor_read_status(const struct device *dev,
|
||||
|
||||
LOG_DBG("Reading status register");
|
||||
|
||||
return memc_flexspi_transfer(data->controller, &transfer);
|
||||
return memc_flexspi_transfer(&data->controller, &transfer);
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_write_status(const struct device *dev,
|
||||
static int flash_flexspi_nor_write_status(struct flash_flexspi_nor_data *data,
|
||||
uint32_t *status)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
|
||||
flexspi_transfer_t transfer = {
|
||||
.deviceAddress = 0,
|
||||
.port = data->port,
|
||||
@@ -216,13 +219,11 @@ static int flash_flexspi_nor_write_status(const struct device *dev,
|
||||
|
||||
LOG_DBG("Writing status register");
|
||||
|
||||
return memc_flexspi_transfer(data->controller, &transfer);
|
||||
return memc_flexspi_transfer(&data->controller, &transfer);
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_write_enable(const struct device *dev)
|
||||
static int flash_flexspi_nor_write_enable(struct flash_flexspi_nor_data *data)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
|
||||
flexspi_transfer_t transfer = {
|
||||
.deviceAddress = 0,
|
||||
.port = data->port,
|
||||
@@ -235,14 +236,12 @@ static int flash_flexspi_nor_write_enable(const struct device *dev)
|
||||
|
||||
LOG_DBG("Enabling write");
|
||||
|
||||
return memc_flexspi_transfer(data->controller, &transfer);
|
||||
return memc_flexspi_transfer(&data->controller, &transfer);
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_erase_sector(const struct device *dev,
|
||||
static int flash_flexspi_nor_erase_sector(struct flash_flexspi_nor_data *data,
|
||||
off_t offset)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
|
||||
flexspi_transfer_t transfer = {
|
||||
.deviceAddress = offset,
|
||||
.port = data->port,
|
||||
@@ -255,14 +254,12 @@ static int flash_flexspi_nor_erase_sector(const struct device *dev,
|
||||
|
||||
LOG_DBG("Erasing sector at 0x%08zx", (ssize_t) offset);
|
||||
|
||||
return memc_flexspi_transfer(data->controller, &transfer);
|
||||
return memc_flexspi_transfer(&data->controller, &transfer);
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_erase_block(const struct device *dev,
|
||||
static int flash_flexspi_nor_erase_block(struct flash_flexspi_nor_data *data,
|
||||
off_t offset)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
|
||||
flexspi_transfer_t transfer = {
|
||||
.deviceAddress = offset,
|
||||
.port = data->port,
|
||||
@@ -275,13 +272,11 @@ static int flash_flexspi_nor_erase_block(const struct device *dev,
|
||||
|
||||
LOG_DBG("Erasing block at 0x%08zx", (ssize_t) offset);
|
||||
|
||||
return memc_flexspi_transfer(data->controller, &transfer);
|
||||
return memc_flexspi_transfer(&data->controller, &transfer);
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_erase_chip(const struct device *dev)
|
||||
static int flash_flexspi_nor_erase_chip(struct flash_flexspi_nor_data *data)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
|
||||
flexspi_transfer_t transfer = {
|
||||
.deviceAddress = 0,
|
||||
.port = data->port,
|
||||
@@ -294,14 +289,12 @@ static int flash_flexspi_nor_erase_chip(const struct device *dev)
|
||||
|
||||
LOG_DBG("Erasing chip");
|
||||
|
||||
return memc_flexspi_transfer(data->controller, &transfer);
|
||||
return memc_flexspi_transfer(&data->controller, &transfer);
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_page_program(const struct device *dev,
|
||||
static int flash_flexspi_nor_page_program(struct flash_flexspi_nor_data *data,
|
||||
off_t offset, const void *buffer, size_t len)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
|
||||
flexspi_transfer_t transfer = {
|
||||
.deviceAddress = offset,
|
||||
.port = data->port,
|
||||
@@ -314,16 +307,16 @@ static int flash_flexspi_nor_page_program(const struct device *dev,
|
||||
|
||||
LOG_DBG("Page programming %d bytes to 0x%08zx", len, (ssize_t) offset);
|
||||
|
||||
return memc_flexspi_transfer(data->controller, &transfer);
|
||||
return memc_flexspi_transfer(&data->controller, &transfer);
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_wait_bus_busy(const struct device *dev)
|
||||
static int flash_flexspi_nor_wait_bus_busy(struct flash_flexspi_nor_data *data)
|
||||
{
|
||||
uint32_t status = 0;
|
||||
int ret;
|
||||
|
||||
do {
|
||||
ret = flash_flexspi_nor_read_status(dev, &status);
|
||||
ret = flash_flexspi_nor_read_status(data, &status);
|
||||
LOG_DBG("status: 0x%x", status);
|
||||
if (ret) {
|
||||
LOG_ERR("Could not read status");
|
||||
@@ -334,14 +327,13 @@ static int flash_flexspi_nor_wait_bus_busy(const struct device *dev)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int flash_flexspi_nor_enable_quad_mode(const struct device *dev)
|
||||
static int flash_flexspi_nor_enable_quad_mode(struct flash_flexspi_nor_data *data)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
uint32_t status = 0x40;
|
||||
|
||||
flash_flexspi_nor_write_status(dev, &status);
|
||||
flash_flexspi_nor_wait_bus_busy(dev);
|
||||
memc_flexspi_reset(data->controller);
|
||||
flash_flexspi_nor_write_status(data, &status);
|
||||
flash_flexspi_nor_wait_bus_busy(data);
|
||||
memc_flexspi_reset(&data->controller);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -350,7 +342,7 @@ static int flash_flexspi_nor_read(const struct device *dev, off_t offset,
|
||||
void *buffer, size_t len)
|
||||
{
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
uint8_t *src = memc_flexspi_get_ahb_address(data->controller,
|
||||
uint8_t *src = memc_flexspi_get_ahb_address(&data->controller,
|
||||
data->port,
|
||||
offset);
|
||||
|
||||
@@ -368,11 +360,11 @@ static int flash_flexspi_nor_write(const struct device *dev, off_t offset,
|
||||
int i;
|
||||
unsigned int key = 0;
|
||||
|
||||
uint8_t *dst = memc_flexspi_get_ahb_address(data->controller,
|
||||
uint8_t *dst = memc_flexspi_get_ahb_address(&data->controller,
|
||||
data->port,
|
||||
offset);
|
||||
|
||||
if (memc_flexspi_is_running_xip(data->controller)) {
|
||||
if (memc_flexspi_is_running_xip(&data->controller)) {
|
||||
/*
|
||||
* ==== ENTER CRITICAL SECTION ====
|
||||
* No flash access should be performed in critical section. All
|
||||
@@ -390,20 +382,20 @@ static int flash_flexspi_nor_write(const struct device *dev, off_t offset,
|
||||
#ifdef CONFIG_FLASH_MCUX_FLEXSPI_NOR_WRITE_BUFFER
|
||||
memcpy(nor_write_buf, src, i);
|
||||
#endif
|
||||
flash_flexspi_nor_write_enable(dev);
|
||||
flash_flexspi_nor_write_enable(data);
|
||||
#ifdef CONFIG_FLASH_MCUX_FLEXSPI_NOR_WRITE_BUFFER
|
||||
flash_flexspi_nor_page_program(dev, offset, nor_write_buf, i);
|
||||
flash_flexspi_nor_page_program(data, offset, nor_write_buf, i);
|
||||
#else
|
||||
flash_flexspi_nor_page_program(dev, offset, src, i);
|
||||
flash_flexspi_nor_page_program(data, offset, src, i);
|
||||
#endif
|
||||
flash_flexspi_nor_wait_bus_busy(dev);
|
||||
memc_flexspi_reset(data->controller);
|
||||
flash_flexspi_nor_wait_bus_busy(data);
|
||||
memc_flexspi_reset(&data->controller);
|
||||
src += i;
|
||||
offset += i;
|
||||
len -= i;
|
||||
}
|
||||
|
||||
if (memc_flexspi_is_running_xip(data->controller)) {
|
||||
if (memc_flexspi_is_running_xip(&data->controller)) {
|
||||
/* ==== EXIT CRITICAL SECTION ==== */
|
||||
irq_unlock(key);
|
||||
}
|
||||
@@ -425,7 +417,7 @@ static int flash_flexspi_nor_erase(const struct device *dev, off_t offset,
|
||||
int i;
|
||||
unsigned int key = 0;
|
||||
|
||||
uint8_t *dst = memc_flexspi_get_ahb_address(data->controller,
|
||||
uint8_t *dst = memc_flexspi_get_ahb_address(&data->controller,
|
||||
data->port,
|
||||
offset);
|
||||
|
||||
@@ -439,7 +431,7 @@ static int flash_flexspi_nor_erase(const struct device *dev, off_t offset,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (memc_flexspi_is_running_xip(data->controller)) {
|
||||
if (memc_flexspi_is_running_xip(&data->controller)) {
|
||||
/*
|
||||
* ==== ENTER CRITICAL SECTION ====
|
||||
* No flash access should be performed in critical section. All
|
||||
@@ -449,29 +441,29 @@ static int flash_flexspi_nor_erase(const struct device *dev, off_t offset,
|
||||
}
|
||||
|
||||
if ((offset == 0) && (size == data->config.flashSize * KB(1))) {
|
||||
flash_flexspi_nor_write_enable(dev);
|
||||
flash_flexspi_nor_erase_chip(dev);
|
||||
flash_flexspi_nor_wait_bus_busy(dev);
|
||||
memc_flexspi_reset(data->controller);
|
||||
flash_flexspi_nor_write_enable(data);
|
||||
flash_flexspi_nor_erase_chip(data);
|
||||
flash_flexspi_nor_wait_bus_busy(data);
|
||||
memc_flexspi_reset(&data->controller);
|
||||
} else if ((0 == (offset % SPI_NOR_BLOCK_SIZE)) && (0 == (size % SPI_NOR_BLOCK_SIZE))) {
|
||||
for (i = 0; i < num_blocks; i++) {
|
||||
flash_flexspi_nor_write_enable(dev);
|
||||
flash_flexspi_nor_erase_block(dev, offset);
|
||||
flash_flexspi_nor_wait_bus_busy(dev);
|
||||
memc_flexspi_reset(data->controller);
|
||||
flash_flexspi_nor_write_enable(data);
|
||||
flash_flexspi_nor_erase_block(data, offset);
|
||||
flash_flexspi_nor_wait_bus_busy(data);
|
||||
memc_flexspi_reset(&data->controller);
|
||||
offset += SPI_NOR_BLOCK_SIZE;
|
||||
}
|
||||
} else {
|
||||
for (i = 0; i < num_sectors; i++) {
|
||||
flash_flexspi_nor_write_enable(dev);
|
||||
flash_flexspi_nor_erase_sector(dev, offset);
|
||||
flash_flexspi_nor_wait_bus_busy(dev);
|
||||
memc_flexspi_reset(data->controller);
|
||||
flash_flexspi_nor_write_enable(data);
|
||||
flash_flexspi_nor_erase_sector(data, offset);
|
||||
flash_flexspi_nor_wait_bus_busy(data);
|
||||
memc_flexspi_reset(&data->controller);
|
||||
offset += SPI_NOR_SECTOR_SIZE;
|
||||
}
|
||||
}
|
||||
|
||||
if (memc_flexspi_is_running_xip(data->controller)) {
|
||||
if (memc_flexspi_is_running_xip(&data->controller)) {
|
||||
/* ==== EXIT CRITICAL SECTION ==== */
|
||||
irq_unlock(key);
|
||||
}
|
||||
@@ -504,17 +496,24 @@ static void flash_flexspi_nor_pages_layout(const struct device *dev,
|
||||
|
||||
static int flash_flexspi_nor_init(const struct device *dev)
|
||||
{
|
||||
const struct flash_flexspi_nor_config *config = dev->config;
|
||||
struct flash_flexspi_nor_data *data = dev->data;
|
||||
uint8_t vendor_id;
|
||||
uint32_t temp_lut[sizeof(flash_flexspi_nor_lut) / sizeof(uint32_t)];
|
||||
|
||||
if (!device_is_ready(data->controller)) {
|
||||
/* First step- use ROM pointer to controller device to create
|
||||
* a copy of the device structure in RAM we can use while in
|
||||
* critical sections of code.
|
||||
*/
|
||||
memcpy(&data->controller, config->controller, sizeof(struct device));
|
||||
|
||||
if (!device_is_ready(&data->controller)) {
|
||||
LOG_ERR("Controller device is not ready");
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
if (!memc_flexspi_is_running_xip(data->controller) &&
|
||||
memc_flexspi_set_device_config(data->controller, &data->config,
|
||||
if (!memc_flexspi_is_running_xip(&data->controller) &&
|
||||
memc_flexspi_set_device_config(&data->controller, &data->config,
|
||||
data->port)) {
|
||||
LOG_ERR("Could not set device configuration");
|
||||
return -EINVAL;
|
||||
@@ -530,22 +529,22 @@ static int flash_flexspi_nor_init(const struct device *dev)
|
||||
memcpy(temp_lut, flash_flexspi_nor_lut,
|
||||
sizeof(flash_flexspi_nor_lut));
|
||||
|
||||
if (memc_flexspi_update_lut(data->controller, 0,
|
||||
if (memc_flexspi_update_lut(&data->controller, 0,
|
||||
(const uint32_t *) temp_lut,
|
||||
sizeof(temp_lut) / sizeof(uint32_t))) {
|
||||
LOG_ERR("Could not update lut");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
memc_flexspi_reset(data->controller);
|
||||
memc_flexspi_reset(&data->controller);
|
||||
|
||||
if (flash_flexspi_nor_get_vendor_id(dev, &vendor_id)) {
|
||||
if (flash_flexspi_nor_get_vendor_id(data, &vendor_id)) {
|
||||
LOG_ERR("Could not read vendor id");
|
||||
return -EIO;
|
||||
}
|
||||
LOG_DBG("Vendor id: 0x%0x", vendor_id);
|
||||
|
||||
if (flash_flexspi_nor_enable_quad_mode(dev)) {
|
||||
if (flash_flexspi_nor_enable_quad_mode(data)) {
|
||||
LOG_ERR("Could not enable quad mode");
|
||||
return -EIO;
|
||||
}
|
||||
@@ -596,9 +595,12 @@ static const struct flash_driver_api flash_flexspi_nor_api = {
|
||||
} \
|
||||
|
||||
#define FLASH_FLEXSPI_NOR(n) \
|
||||
static const struct flash_flexspi_nor_config \
|
||||
flash_flexspi_nor_config_##n = { \
|
||||
.controller = DEVICE_DT_GET(DT_INST_BUS(n)), \
|
||||
}; \
|
||||
static struct flash_flexspi_nor_data \
|
||||
flash_flexspi_nor_data_##n = { \
|
||||
.controller = DEVICE_DT_GET(DT_INST_BUS(n)), \
|
||||
.config = FLASH_FLEXSPI_DEVICE_CONFIG(n), \
|
||||
.port = DT_INST_REG_ADDR(n), \
|
||||
.layout = { \
|
||||
@@ -616,7 +618,7 @@ static const struct flash_driver_api flash_flexspi_nor_api = {
|
||||
flash_flexspi_nor_init, \
|
||||
NULL, \
|
||||
&flash_flexspi_nor_data_##n, \
|
||||
NULL, \
|
||||
&flash_flexspi_nor_config_##n, \
|
||||
POST_KERNEL, \
|
||||
CONFIG_FLASH_INIT_PRIORITY, \
|
||||
&flash_flexspi_nor_api);
|
||||
|
||||
@@ -70,7 +70,7 @@ static int riscv_plic_is_edge_irq(uint32_t irq)
|
||||
volatile uint32_t *trig = (volatile uint32_t *)PLIC_EDGE_TRIG_TYPE;
|
||||
|
||||
trig += (irq >> PLIC_EDGE_TRIG_SHIFT);
|
||||
return *trig & BIT(irq);
|
||||
return *trig & BIT(irq & BIT_MASK(PLIC_EDGE_TRIG_SHIFT));
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -16,10 +16,8 @@
|
||||
#include <zephyr/drivers/interrupt_controller/intc_mchp_xec_ecia.h>
|
||||
#endif
|
||||
#include <zephyr/drivers/pinctrl.h>
|
||||
#ifdef CONFIG_PM_DEVICE
|
||||
#include <zephyr/pm/device.h>
|
||||
#include <zephyr/pm/policy.h>
|
||||
#endif
|
||||
#include <zephyr/drivers/ps2.h>
|
||||
#include <soc.h>
|
||||
#include <zephyr/logging/log.h>
|
||||
|
||||
@@ -19,6 +19,7 @@ LOG_MODULE_REGISTER(ams_as5600, CONFIG_SENSOR_LOG_LEVEL);
|
||||
#define AS5600_ANGLE_REGISTER_H 0x0E
|
||||
#define AS5600_FULL_ANGLE 360
|
||||
#define AS5600_PULSES_PER_REV 4096
|
||||
#define AS5600_MILLION_UNIT 1000000
|
||||
|
||||
struct as5600_dev_cfg {
|
||||
struct i2c_dt_spec i2c_port;
|
||||
@@ -60,8 +61,8 @@ static int as5600_get(const struct device *dev, enum sensor_channel chan,
|
||||
val->val1 = ((int32_t)dev_data->position * AS5600_FULL_ANGLE) /
|
||||
AS5600_PULSES_PER_REV;
|
||||
|
||||
val->val2 = ((int32_t)dev_data->position * AS5600_FULL_ANGLE) -
|
||||
(val->val1 * AS5600_PULSES_PER_REV);
|
||||
val->val2 = (((int32_t)dev_data->position * AS5600_FULL_ANGLE) %
|
||||
AS5600_PULSES_PER_REV) * (AS5600_MILLION_UNIT / AS5600_PULSES_PER_REV);
|
||||
} else {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
@@ -7,7 +7,8 @@ config TEMP_KINETIS
|
||||
bool "NXP Kinetis Temperature Sensor"
|
||||
default y
|
||||
depends on DT_HAS_NXP_KINETIS_TEMPERATURE_ENABLED
|
||||
depends on (ADC && SOC_FAMILY_KINETIS)
|
||||
depends on SOC_FAMILY_KINETIS
|
||||
select ADC
|
||||
help
|
||||
Enable driver for NXP Kinetis temperature sensor.
|
||||
|
||||
|
||||
@@ -159,7 +159,7 @@ static int temp_kinetis_init(const struct device *dev)
|
||||
},
|
||||
};
|
||||
|
||||
memset(&data->buffer, 0, ARRAY_SIZE(data->buffer));
|
||||
memset(&data->buffer, 0, sizeof(data->buffer));
|
||||
|
||||
if (!device_is_ready(config->adc)) {
|
||||
LOG_ERR("ADC device is not ready");
|
||||
|
||||
@@ -225,13 +225,18 @@ static int spi_mcux_configure(const struct device *dev,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* Setting the baud rate in LPSPI_MasterInit requires module to be disabled */
|
||||
LPSPI_Enable(base, false);
|
||||
while ((base->CR & LPSPI_CR_MEN_MASK) != 0U) {
|
||||
/* Wait until LPSPI is disabled. Datasheet:
|
||||
* After writing 0, MEN (Module Enable) remains set until the LPSPI has completed
|
||||
* the current transfer and is idle.
|
||||
if (data->ctx.config != NULL) {
|
||||
/* Setting the baud rate in LPSPI_MasterInit requires module to be disabled. Only
|
||||
* disable if already configured, otherwise the clock is not enabled and the
|
||||
* CR register cannot be written.
|
||||
*/
|
||||
LPSPI_Enable(base, false);
|
||||
while ((base->CR & LPSPI_CR_MEN_MASK) != 0U) {
|
||||
/* Wait until LPSPI is disabled. Datasheet:
|
||||
* After writing 0, MEN (Module Enable) remains set until the LPSPI has
|
||||
* completed the current transfer and is idle.
|
||||
*/
|
||||
}
|
||||
}
|
||||
|
||||
LPSPI_MasterInit(base, &master_config, clock_freq);
|
||||
|
||||
@@ -66,4 +66,10 @@ config IVSHMEM_V2
|
||||
Enable ivshmem-v2 support.
|
||||
ivshmem-v2 is primarily used for IPC in the Jailhouse hypervisor.
|
||||
|
||||
config IVSHMEM_V2_MAX_PEERS
|
||||
int "Maximum number of ivshmem-v2 peers"
|
||||
depends on IVSHMEM_V2
|
||||
default 2
|
||||
range 2 65536
|
||||
|
||||
endif # VIRTUALIZATION
|
||||
|
||||
@@ -198,7 +198,7 @@ static bool ivshmem_configure(const struct device *dev)
|
||||
(volatile struct ivshmem_v2_reg *)DEVICE_MMIO_GET(dev);
|
||||
|
||||
data->max_peers = regs->max_peers;
|
||||
if (!IN_RANGE(data->max_peers, 2, 0x10000)) {
|
||||
if (!IN_RANGE(data->max_peers, 2, CONFIG_IVSHMEM_V2_MAX_PEERS)) {
|
||||
LOG_ERR("Invalid max peers %u", data->max_peers);
|
||||
return false;
|
||||
}
|
||||
@@ -211,26 +211,49 @@ static bool ivshmem_configure(const struct device *dev)
|
||||
shmem_phys_addr = pcie_conf_read_u64(data->pcie->bdf, cap_pos);
|
||||
}
|
||||
|
||||
/* State table R/O */
|
||||
cap_pos = vendor_cap + IVSHMEM_CFG_STATE_TAB_SZ / 4;
|
||||
size_t state_table_size = pcie_conf_read(data->pcie->bdf, cap_pos);
|
||||
|
||||
LOG_INF("State table size 0x%zX", state_table_size);
|
||||
if (state_table_size < sizeof(uint32_t) * data->max_peers) {
|
||||
LOG_ERR("Invalid state table size %zu", state_table_size);
|
||||
return false;
|
||||
}
|
||||
z_phys_map((uint8_t **)&data->state_table_shmem,
|
||||
shmem_phys_addr, state_table_size,
|
||||
K_MEM_CACHE_WB | K_MEM_PERM_USER);
|
||||
|
||||
/* R/W section (optional) */
|
||||
cap_pos = vendor_cap + IVSHMEM_CFG_RW_SECTION_SZ / 4;
|
||||
data->rw_section_size = pcie_conf_read_u64(data->pcie->bdf, cap_pos);
|
||||
data->rw_section_offset = state_table_size;
|
||||
size_t rw_section_offset = state_table_size;
|
||||
LOG_INF("RW section size 0x%zX", data->rw_section_size);
|
||||
if (data->rw_section_size > 0) {
|
||||
z_phys_map((uint8_t **)&data->rw_section_shmem,
|
||||
shmem_phys_addr + rw_section_offset, data->rw_section_size,
|
||||
K_MEM_CACHE_WB | K_MEM_PERM_RW | K_MEM_PERM_USER);
|
||||
}
|
||||
|
||||
/* Output sections */
|
||||
cap_pos = vendor_cap + IVSHMEM_CFG_OUTPUT_SECTION_SZ / 4;
|
||||
data->output_section_size = pcie_conf_read_u64(data->pcie->bdf, cap_pos);
|
||||
data->output_section_offset = data->rw_section_offset + data->rw_section_size;
|
||||
size_t output_section_offset = rw_section_offset + data->rw_section_size;
|
||||
LOG_INF("Output section size 0x%zX", data->output_section_size);
|
||||
for (uint32_t i = 0; i < data->max_peers; i++) {
|
||||
uintptr_t phys_addr = shmem_phys_addr +
|
||||
output_section_offset +
|
||||
(data->output_section_size * i);
|
||||
uint32_t flags = K_MEM_CACHE_WB | K_MEM_PERM_USER;
|
||||
|
||||
data->size = data->output_section_offset +
|
||||
/* Only your own output section is R/W */
|
||||
if (i == regs->id) {
|
||||
flags |= K_MEM_PERM_RW;
|
||||
}
|
||||
z_phys_map((uint8_t **)&data->output_section_shmem[i],
|
||||
phys_addr, data->output_section_size, flags);
|
||||
}
|
||||
|
||||
data->size = output_section_offset +
|
||||
data->output_section_size * data->max_peers;
|
||||
|
||||
/* Ensure one-shot ISR mode is disabled */
|
||||
@@ -249,11 +272,11 @@ static bool ivshmem_configure(const struct device *dev)
|
||||
}
|
||||
|
||||
data->size = mbar_shmem.size;
|
||||
}
|
||||
|
||||
z_phys_map((uint8_t **)&data->shmem,
|
||||
shmem_phys_addr, data->size,
|
||||
K_MEM_CACHE_WB | K_MEM_PERM_RW | K_MEM_PERM_USER);
|
||||
z_phys_map((uint8_t **)&data->shmem,
|
||||
shmem_phys_addr, data->size,
|
||||
K_MEM_CACHE_WB | K_MEM_PERM_RW | K_MEM_PERM_USER);
|
||||
}
|
||||
|
||||
if (msi_x_bar_present) {
|
||||
if (!ivshmem_configure_msi_x_interrupts(dev)) {
|
||||
@@ -284,6 +307,13 @@ static size_t ivshmem_api_get_mem(const struct device *dev,
|
||||
{
|
||||
struct ivshmem *data = dev->data;
|
||||
|
||||
#ifdef CONFIG_IVSHMEM_V2
|
||||
if (data->ivshmem_v2) {
|
||||
*memmap = 0;
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
*memmap = data->shmem;
|
||||
|
||||
return data->size;
|
||||
@@ -389,11 +419,11 @@ static size_t ivshmem_api_get_rw_mem_section(const struct device *dev,
|
||||
struct ivshmem *data = dev->data;
|
||||
|
||||
if (!data->ivshmem_v2) {
|
||||
memmap = NULL;
|
||||
*memmap = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
*memmap = data->shmem + data->rw_section_offset;
|
||||
*memmap = data->rw_section_shmem;
|
||||
|
||||
return data->rw_section_size;
|
||||
}
|
||||
@@ -405,12 +435,11 @@ static size_t ivshmem_api_get_output_mem_section(const struct device *dev,
|
||||
struct ivshmem *data = dev->data;
|
||||
|
||||
if (!data->ivshmem_v2 || peer_id >= data->max_peers) {
|
||||
memmap = NULL;
|
||||
*memmap = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
*memmap = data->shmem + data->output_section_offset +
|
||||
data->output_section_size * peer_id;
|
||||
*memmap = data->output_section_shmem[peer_id];
|
||||
|
||||
return data->output_section_size;
|
||||
}
|
||||
@@ -425,7 +454,7 @@ static uint32_t ivshmem_api_get_state(const struct device *dev,
|
||||
}
|
||||
|
||||
const volatile uint32_t *state_table =
|
||||
(const volatile uint32_t *)data->shmem;
|
||||
(const volatile uint32_t *)data->state_table_shmem;
|
||||
|
||||
return state_table[peer_id];
|
||||
}
|
||||
|
||||
@@ -57,9 +57,10 @@ struct ivshmem {
|
||||
bool ivshmem_v2;
|
||||
uint32_t max_peers;
|
||||
size_t rw_section_size;
|
||||
size_t rw_section_offset;
|
||||
size_t output_section_size;
|
||||
size_t output_section_offset;
|
||||
uintptr_t state_table_shmem;
|
||||
uintptr_t rw_section_shmem;
|
||||
uintptr_t output_section_shmem[CONFIG_IVSHMEM_V2_MAX_PEERS];
|
||||
#endif
|
||||
};
|
||||
|
||||
|
||||
@@ -61,8 +61,8 @@
|
||||
reg = <0x5000d000 0x400>;
|
||||
num-lines = <16>;
|
||||
interrupts = <6 0>, <7 0>, <8 0>, <9 0>,
|
||||
<10 0>, <23 0>, <40 0>, <42 0>,
|
||||
<64 0>, <65 0>, <66 0>, <67 0>,
|
||||
<10 0>, <23 0>, <64 0>, <65 0>,
|
||||
<66 0>, <67 0>, <40 0>, <42 0>,
|
||||
<76 0>, <77 0>, <121 0>, <127 0>;
|
||||
interrupt-names = "line0", "line1", "line2", "line3",
|
||||
"line4", "line5", "line6", "line7",
|
||||
|
||||
@@ -47,6 +47,3 @@ properties:
|
||||
description: |
|
||||
Initial time quanta of phase buffer 2 segment for the data phase (ISO11898-1:2015). Deprecated
|
||||
in favor of setting advanced timing parameters from the application.
|
||||
tx-delay-comp-offset:
|
||||
type: int
|
||||
default: 0
|
||||
|
||||
@@ -175,10 +175,10 @@ int acpi_drhd_get(enum AcpiDmarScopeType scope, struct acpi_dmar_device_scope *d
|
||||
union acpi_dmar_id *dmar_id, int *num_inst, int max_inst);
|
||||
|
||||
/**
|
||||
* @brief Retrieve lapic info for a specific cpu.
|
||||
* @brief Retrieve the 'n'th enabled local apic info.
|
||||
*
|
||||
* @param cpu_num the cpu number
|
||||
* @return lapic info on success or NULL
|
||||
* @return local apic info on success or NULL otherwise
|
||||
*/
|
||||
struct acpi_madt_local_apic *acpi_local_apic_get(uint32_t cpu_num);
|
||||
struct acpi_madt_local_apic *acpi_local_apic_get(int cpu_num);
|
||||
#endif
|
||||
|
||||
@@ -318,6 +318,23 @@ typedef void (*can_state_change_callback_t)(const struct device *dev,
|
||||
* For internal driver use only, skip these in public documentation.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief Calculate Transmitter Delay Compensation Offset from data phase timing parameters.
|
||||
*
|
||||
* Calculates the TDC Offset in minimum time quanta (mtq) using the sample point and CAN core clock
|
||||
* prescaler specified by a set of data phase timing parameters.
|
||||
*
|
||||
* The result is clamped to the minimum/maximum supported TDC Offset values provided.
|
||||
*
|
||||
* @param _timing_data Pointer to data phase timing parameters.
|
||||
* @param _tdco_min Minimum supported TDC Offset value in mtq.
|
||||
* @param _tdco_max Maximum supported TDC Offset value in mtq.
|
||||
* @return Calculated TDC Offset value in mtq.
|
||||
*/
|
||||
#define CAN_CALC_TDCO(_timing_data, _tdco_min, _tdco_max) \
|
||||
CLAMP((1U + _timing_data->prop_seg + _timing_data->phase_seg1) * _timing_data->prescaler, \
|
||||
_tdco_min, _tdco_max)
|
||||
|
||||
/**
|
||||
* @brief Callback API upon setting CAN bus timing
|
||||
* See @a can_set_timing() for argument description
|
||||
|
||||
@@ -640,7 +640,7 @@ enum can_mcan_psr_lec {
|
||||
*/
|
||||
#define CAN_MCAN_DT_MRAM_DEFINE(node_id, _name) \
|
||||
BUILD_ASSERT(CAN_MCAN_DT_MRAM_OFFSET(node_id) == 0, "offset must be 0"); \
|
||||
static char __noinit __nocache __aligned(4) _name[CAN_MCAN_DT_MRAM_ELEMENTS_SIZE(node_id)];
|
||||
static char __nocache_noinit __aligned(4) _name[CAN_MCAN_DT_MRAM_ELEMENTS_SIZE(node_id)];
|
||||
|
||||
/**
|
||||
* @brief Assert that the Message RAM configuration meets the Bosch M_CAN IP core restrictions
|
||||
@@ -1253,7 +1253,6 @@ struct can_mcan_config {
|
||||
uint8_t sjw_data;
|
||||
uint8_t prop_ts1_data;
|
||||
uint8_t ts2_data;
|
||||
uint8_t tx_delay_comp_offset;
|
||||
#endif
|
||||
const struct device *phy;
|
||||
uint32_t max_bitrate;
|
||||
@@ -1327,7 +1326,6 @@ struct can_mcan_config {
|
||||
.prop_ts1_data = DT_PROP_OR(node_id, prop_seg_data, 0) + \
|
||||
DT_PROP_OR(node_id, phase_seg1_data, 0), \
|
||||
.ts2_data = DT_PROP_OR(node_id, phase_seg2_data, 0), \
|
||||
.tx_delay_comp_offset = DT_PROP(node_id, tx_delay_comp_offset), \
|
||||
.phy = DEVICE_DT_GET_OR_NULL(DT_PHANDLE(node_id, phys)), \
|
||||
.max_bitrate = DT_CAN_TRANSCEIVER_MAX_BITRATE(node_id, 8000000), \
|
||||
.custom = _custom, \
|
||||
|
||||
@@ -84,6 +84,12 @@ __subsystem struct ivshmem_driver_api {
|
||||
/**
|
||||
* @brief Get the inter-VM shared memory
|
||||
*
|
||||
* Note: This API is not supported for ivshmem-v2, as
|
||||
* the R/W and R/O areas may not be mapped contiguously.
|
||||
* For ivshmem-v2, use the ivshmem_get_rw_mem_section,
|
||||
* ivshmem_get_output_mem_section and ivshmem_get_state
|
||||
* APIs to access the shared memory.
|
||||
*
|
||||
* @param dev Pointer to the device structure for the driver instance
|
||||
* @param memmap A pointer to fill in with the memory address
|
||||
*
|
||||
|
||||
@@ -40,6 +40,11 @@
|
||||
/* TODO: does this section require alignment? */
|
||||
KEEP(*(_SHARED_SW_ISR_TABLE_SECTION_SYMS))
|
||||
} GROUP_ROM_LINK_IN(RAMABLE_REGION, ROMABLE_REGION)
|
||||
|
||||
SECTION_PROLOGUE(.text.z_shared_isr,,)
|
||||
{
|
||||
KEEP(*(.text.z_shared_isr))
|
||||
} GROUP_ROM_LINK_IN(RAMABLE_REGION, ROMABLE_REGION)
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
@@ -49,8 +49,10 @@
|
||||
|
||||
#if defined(CONFIG_NOCACHE_MEMORY)
|
||||
#define __nocache __in_section_unique(_NOCACHE_SECTION_NAME)
|
||||
#define __nocache_noinit __nocache
|
||||
#else
|
||||
#define __nocache
|
||||
#define __nocache_noinit __noinit
|
||||
#endif /* CONFIG_NOCACHE_MEMORY */
|
||||
|
||||
#if defined(CONFIG_KERNEL_COHERENCE)
|
||||
|
||||
@@ -153,8 +153,12 @@ static inline uintptr_t z_mem_phys_addr(void *virt)
|
||||
#if CONFIG_KERNEL_VM_BASE != 0
|
||||
(addr >= CONFIG_KERNEL_VM_BASE) &&
|
||||
#endif
|
||||
#if (CONFIG_KERNEL_VM_BASE + CONFIG_KERNEL_VM_SIZE) != 0
|
||||
(addr < (CONFIG_KERNEL_VM_BASE +
|
||||
(CONFIG_KERNEL_VM_SIZE))),
|
||||
#else
|
||||
false,
|
||||
#endif
|
||||
"address %p not in permanent mappings", virt);
|
||||
#else
|
||||
/* Should be identity-mapped */
|
||||
@@ -162,8 +166,12 @@ static inline uintptr_t z_mem_phys_addr(void *virt)
|
||||
#if CONFIG_SRAM_BASE_ADDRESS != 0
|
||||
(addr >= CONFIG_SRAM_BASE_ADDRESS) &&
|
||||
#endif
|
||||
#if (CONFIG_SRAM_BASE_ADDRESS + (CONFIG_SRAM_SIZE * 1024UL)) != 0
|
||||
(addr < (CONFIG_SRAM_BASE_ADDRESS +
|
||||
(CONFIG_SRAM_SIZE * 1024UL))),
|
||||
#else
|
||||
false,
|
||||
#endif
|
||||
"physical address 0x%lx not in RAM",
|
||||
(unsigned long)addr);
|
||||
#endif /* CONFIG_MMU */
|
||||
@@ -182,8 +190,12 @@ static inline void *z_mem_virt_addr(uintptr_t phys)
|
||||
#if CONFIG_SRAM_BASE_ADDRESS != 0
|
||||
(phys >= CONFIG_SRAM_BASE_ADDRESS) &&
|
||||
#endif
|
||||
#if (CONFIG_SRAM_BASE_ADDRESS + (CONFIG_SRAM_SIZE * 1024UL)) != 0
|
||||
(phys < (CONFIG_SRAM_BASE_ADDRESS +
|
||||
(CONFIG_SRAM_SIZE * 1024UL))),
|
||||
#else
|
||||
false,
|
||||
#endif
|
||||
"physical address 0x%lx not in RAM", (unsigned long)phys);
|
||||
|
||||
/* TODO add assertion that this page frame is pinned to boot mapping,
|
||||
|
||||
@@ -141,7 +141,15 @@ void z_impl_k_timer_start(struct k_timer *timer, k_timeout_t duration,
|
||||
{
|
||||
SYS_PORT_TRACING_OBJ_FUNC(k_timer, start, timer, duration, period);
|
||||
|
||||
/* Acquire spinlock to ensure safety during concurrent calls to
|
||||
* k_timer_start for scheduling or rescheduling. This is necessary
|
||||
* since k_timer_start can be preempted, especially for the same
|
||||
* timer instance.
|
||||
*/
|
||||
k_spinlock_key_t key = k_spin_lock(&lock);
|
||||
|
||||
if (K_TIMEOUT_EQ(duration, K_FOREVER)) {
|
||||
k_spin_unlock(&lock, key);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -168,6 +176,8 @@ void z_impl_k_timer_start(struct k_timer *timer, k_timeout_t duration,
|
||||
|
||||
z_add_timeout(&timer->timeout, z_timer_expiration_handler,
|
||||
duration);
|
||||
|
||||
k_spin_unlock(&lock, key);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_USERSPACE
|
||||
|
||||
@@ -14,6 +14,12 @@ module = ACPI
|
||||
module-str = acpi
|
||||
source "subsys/logging/Kconfig.template.log_config"
|
||||
|
||||
config ACPI_PRT_BUS_NAME
|
||||
string "ACPI name of PCI bus"
|
||||
default "_SB.PCI0"
|
||||
help
|
||||
ACPI name of PCI bus.
|
||||
|
||||
config ACPI_MAX_PRT_ENTRY
|
||||
int "Size of PRT buffer"
|
||||
default 4096
|
||||
|
||||
@@ -52,24 +52,6 @@ static void notify_handler(ACPI_HANDLE device, UINT32 value, void *ctx)
|
||||
ACPI_INFO(("Received a notify 0x%X", value));
|
||||
}
|
||||
|
||||
static ACPI_STATUS region_handler(UINT32 Function, ACPI_PHYSICAL_ADDRESS address, UINT32 bit_width,
|
||||
UINT64 *value, void *handler_ctx, void *region_ctx)
|
||||
{
|
||||
return AE_OK;
|
||||
}
|
||||
|
||||
static ACPI_STATUS region_init(ACPI_HANDLE RegionHandle, UINT32 Function, void *handler_ctx,
|
||||
void **region_ctx)
|
||||
{
|
||||
if (Function == ACPI_REGION_DEACTIVATE) {
|
||||
*region_ctx = NULL;
|
||||
} else {
|
||||
*region_ctx = RegionHandle;
|
||||
}
|
||||
|
||||
return AE_OK;
|
||||
}
|
||||
|
||||
static ACPI_STATUS install_handlers(void)
|
||||
{
|
||||
ACPI_STATUS status;
|
||||
@@ -82,13 +64,7 @@ static ACPI_STATUS install_handlers(void)
|
||||
goto exit;
|
||||
}
|
||||
|
||||
status = AcpiInstallAddressSpaceHandler(ACPI_ROOT_OBJECT, ACPI_ADR_SPACE_SYSTEM_MEMORY,
|
||||
region_handler, region_init, NULL);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
ACPI_EXCEPTION((AE_INFO, status, "While installing an OpRegion handler"));
|
||||
}
|
||||
exit:
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
@@ -115,10 +91,10 @@ static ACPI_STATUS initialize_acpica(void)
|
||||
goto exit;
|
||||
}
|
||||
|
||||
/* Initialize the ACPI hardware */
|
||||
status = AcpiEnableSubsystem(ACPI_FULL_INITIALIZATION);
|
||||
/* Create the ACPI namespace from ACPI tables */
|
||||
status = AcpiLoadTables();
|
||||
if (ACPI_FAILURE(status)) {
|
||||
ACPI_EXCEPTION((AE_INFO, status, "While enabling ACPI"));
|
||||
ACPI_EXCEPTION((AE_INFO, status, "While loading ACPI tables"));
|
||||
goto exit;
|
||||
}
|
||||
|
||||
@@ -129,10 +105,10 @@ static ACPI_STATUS initialize_acpica(void)
|
||||
goto exit;
|
||||
}
|
||||
|
||||
/* Create the ACPI namespace from ACPI tables */
|
||||
status = AcpiLoadTables();
|
||||
/* Initialize the ACPI hardware */
|
||||
status = AcpiEnableSubsystem(ACPI_FULL_INITIALIZATION);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
ACPI_EXCEPTION((AE_INFO, status, "While loading ACPI tables"));
|
||||
ACPI_EXCEPTION((AE_INFO, status, "While enabling ACPI"));
|
||||
goto exit;
|
||||
}
|
||||
|
||||
@@ -239,7 +215,7 @@ static int acpi_get_irq_table(struct acpi *bus, char *bus_name,
|
||||
}
|
||||
|
||||
rt_buffer.Pointer = rt_table;
|
||||
rt_buffer.Length = ACPI_DEBUG_BUFFER_SIZE;
|
||||
rt_buffer.Length = rt_size;
|
||||
|
||||
status = AcpiGetIrqRoutingTable(node, &rt_buffer);
|
||||
if (ACPI_FAILURE(status)) {
|
||||
@@ -263,7 +239,8 @@ static int acpi_get_irq_table(struct acpi *bus, char *bus_name,
|
||||
static int acpi_retrieve_legacy_irq(struct acpi *bus)
|
||||
{
|
||||
/* TODO: assume platform have only one PCH with single PCI bus (bus 0). */
|
||||
return acpi_get_irq_table(bus, "_SB.PC00", bus->pci_prt_table, sizeof(bus->pci_prt_table));
|
||||
return acpi_get_irq_table(bus, CONFIG_ACPI_PRT_BUS_NAME,
|
||||
bus->pci_prt_table, sizeof(bus->pci_prt_table));
|
||||
}
|
||||
|
||||
static ACPI_STATUS dev_resource_enum_callback(ACPI_HANDLE obj_handle, UINT32 level, void *ctx,
|
||||
@@ -791,10 +768,13 @@ int acpi_drhd_get(enum AcpiDmarScopeType scope, struct acpi_dmar_device_scope *d
|
||||
return 0;
|
||||
}
|
||||
|
||||
struct acpi_madt_local_apic *acpi_local_apic_get(uint32_t cpu_num)
|
||||
#define ACPI_CPU_FLAGS_ENABLED 0x01u
|
||||
|
||||
struct acpi_madt_local_apic *acpi_local_apic_get(int cpu_num)
|
||||
{
|
||||
struct acpi_madt_local_apic *lapic;
|
||||
int cpu_cnt;
|
||||
int idx;
|
||||
|
||||
if (acpi_madt_entry_get(ACPI_MADT_TYPE_LOCAL_APIC, (ACPI_SUBTABLE_HEADER **)&lapic,
|
||||
&cpu_cnt)) {
|
||||
@@ -802,10 +782,15 @@ struct acpi_madt_local_apic *acpi_local_apic_get(uint32_t cpu_num)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if ((cpu_num >= cpu_cnt) || !(lapic[cpu_num].LapicFlags & 1u)) {
|
||||
/* Proccessor not enabled. */
|
||||
return NULL;
|
||||
for (idx = 0; cpu_num >= 0 && idx < cpu_cnt; idx++) {
|
||||
if (lapic[idx].LapicFlags & ACPI_CPU_FLAGS_ENABLED) {
|
||||
if (cpu_num == 0) {
|
||||
return &lapic[idx];
|
||||
}
|
||||
|
||||
cpu_num--;
|
||||
}
|
||||
}
|
||||
|
||||
return &lapic[cpu_num];
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#include <zephyr/posix/pthread.h>
|
||||
#include <zephyr/posix/pthread_key.h>
|
||||
#include <zephyr/sys/bitarray.h>
|
||||
#include <zephyr/sys/__assert.h>
|
||||
|
||||
struct pthread_key_data {
|
||||
sys_snode_t node;
|
||||
@@ -120,6 +121,8 @@ int pthread_key_create(pthread_key_t *key,
|
||||
*/
|
||||
int pthread_key_delete(pthread_key_t key)
|
||||
{
|
||||
size_t bit;
|
||||
__unused int ret;
|
||||
pthread_key_obj *key_obj;
|
||||
struct pthread_key_data *key_data;
|
||||
sys_snode_t *node_l, *next_node_l;
|
||||
@@ -145,7 +148,9 @@ int pthread_key_delete(pthread_key_t key)
|
||||
k_free((void *)key_data);
|
||||
}
|
||||
|
||||
(void)sys_bitarray_free(&posix_key_bitarray, 1, 0);
|
||||
bit = posix_key_to_offset(key_obj);
|
||||
ret = sys_bitarray_free(&posix_key_bitarray, 1, bit);
|
||||
__ASSERT_NO_MSG(ret == 0);
|
||||
|
||||
k_spin_unlock(&pthread_key_lock, key_key);
|
||||
|
||||
|
||||
@@ -628,6 +628,8 @@ void pthread_exit(void *retval)
|
||||
/* not a valid posix_thread */
|
||||
LOG_DBG("Aborting non-pthread %p", k_current_get());
|
||||
k_thread_abort(k_current_get());
|
||||
|
||||
CODE_UNREACHABLE;
|
||||
}
|
||||
|
||||
/* Make a thread as cancelable before exiting */
|
||||
|
||||
@@ -22,6 +22,7 @@ extern "C" {
|
||||
#include <zephyr/types.h>
|
||||
#include <zephyr/device.h>
|
||||
#include <zephyr/toolchain.h>
|
||||
#include <zephyr/dsp/types.h> /* float32_t, float64_t */
|
||||
|
||||
/* Use static variables instead of calloc() */
|
||||
#define CO_USE_GLOBALS
|
||||
@@ -46,12 +47,13 @@ extern "C" {
|
||||
#endif
|
||||
|
||||
typedef bool bool_t;
|
||||
typedef float float32_t;
|
||||
typedef long double float64_t;
|
||||
typedef char char_t;
|
||||
typedef unsigned char oChar_t;
|
||||
typedef unsigned char domain_t;
|
||||
|
||||
BUILD_ASSERT(sizeof(float32_t) >= 4);
|
||||
BUILD_ASSERT(sizeof(float64_t) >= 8);
|
||||
|
||||
typedef struct canopen_rx_msg {
|
||||
uint8_t data[8];
|
||||
uint16_t ident;
|
||||
|
||||
@@ -149,6 +149,8 @@ void inferenceProcessTask(void *_name, void *heap, void *_params)
|
||||
}
|
||||
|
||||
k_thread_abort(k_current_get());
|
||||
|
||||
CODE_UNREACHABLE;
|
||||
}
|
||||
|
||||
/* inferenceSenderTask - Creates NUM_INFERENCE_JOBS jobs, queues them, and then
|
||||
|
||||
@@ -23,9 +23,7 @@ ISR_FLAG_DIRECT = 1 << 0
|
||||
# into 1 line which then goes into the 1st level)
|
||||
# 0x00FF0000 - represents the 3rd level (i.e. the interrupts funnel
|
||||
# into 1 line which then goes into the 2nd level)
|
||||
FIRST_LVL_INTERRUPTS = 0x000000FF
|
||||
SECND_LVL_INTERRUPTS = 0x0000FF00
|
||||
THIRD_LVL_INTERRUPTS = 0x00FF0000
|
||||
INTERRUPT_LVL_BITMASK = [0x000000FF, 0x0000FF00, 0x00FF0000]
|
||||
|
||||
INTERRUPT_BITS = [8, 8, 8]
|
||||
|
||||
@@ -269,16 +267,18 @@ def bit_mask(bits):
|
||||
return mask
|
||||
|
||||
def update_masks():
|
||||
global FIRST_LVL_INTERRUPTS
|
||||
global SECND_LVL_INTERRUPTS
|
||||
global THIRD_LVL_INTERRUPTS
|
||||
|
||||
if sum(INTERRUPT_BITS) > 32:
|
||||
raise ValueError("Too many interrupt bits")
|
||||
|
||||
FIRST_LVL_INTERRUPTS = bit_mask(INTERRUPT_BITS[0])
|
||||
SECND_LVL_INTERRUPTS = bit_mask(INTERRUPT_BITS[1]) << INTERRUPT_BITS[0]
|
||||
THIRD_LVL_INTERRUPTS = bit_mask(INTERRUPT_BITS[2]) << INTERRUPT_BITS[0] + INTERRUPT_BITS[2]
|
||||
INTERRUPT_LVL_BITMASK[0] = bit_mask(INTERRUPT_BITS[0])
|
||||
INTERRUPT_LVL_BITMASK[1] = bit_mask(INTERRUPT_BITS[1]) << INTERRUPT_BITS[0]
|
||||
INTERRUPT_LVL_BITMASK[2] = bit_mask(INTERRUPT_BITS[2]) << INTERRUPT_BITS[0] + INTERRUPT_BITS[1]
|
||||
|
||||
debug("Level Bits Bitmask")
|
||||
debug("----------------------------")
|
||||
for i in range(3):
|
||||
bitmask_str = "0x" + format(INTERRUPT_LVL_BITMASK[i], '08X')
|
||||
debug(f"{i + 1:>5} {INTERRUPT_BITS[i]:>7} {bitmask_str:>14}")
|
||||
|
||||
def main():
|
||||
parse_args()
|
||||
@@ -368,9 +368,9 @@ def main():
|
||||
else:
|
||||
# Figure out third level interrupt position
|
||||
debug('IRQ = ' + hex(irq))
|
||||
irq3 = (irq & THIRD_LVL_INTERRUPTS) >> INTERRUPT_BITS[0] + INTERRUPT_BITS[1]
|
||||
irq2 = (irq & SECND_LVL_INTERRUPTS) >> INTERRUPT_BITS[0]
|
||||
irq1 = irq & FIRST_LVL_INTERRUPTS
|
||||
irq3 = (irq & INTERRUPT_LVL_BITMASK[2]) >> INTERRUPT_BITS[0] + INTERRUPT_BITS[1]
|
||||
irq2 = (irq & INTERRUPT_LVL_BITMASK[1]) >> INTERRUPT_BITS[0]
|
||||
irq1 = irq & INTERRUPT_LVL_BITMASK[0]
|
||||
|
||||
if irq3:
|
||||
irq_parent = irq2
|
||||
|
||||
@@ -19,7 +19,7 @@ lpc_checksum
|
||||
Pillow>=10.0
|
||||
|
||||
# can be used to sign a Zephyr application binary for consumption by a bootloader
|
||||
imgtool>=1.9
|
||||
imgtool>=2.0.0
|
||||
|
||||
# used by nanopb module to generate sources from .proto files
|
||||
grpcio-tools>=1.47.0
|
||||
|
||||
@@ -56,7 +56,7 @@ class Snippet:
|
||||
path = pathobj.parent / value
|
||||
if not path.is_file():
|
||||
_err(f'snippet file {pathobj}: {variable}: file not found: {path}')
|
||||
return f'"{path}"'
|
||||
return f'"{path.as_posix()}"'
|
||||
if variable in ('DTS_EXTRA_CPPFLAGS'):
|
||||
return f'"{value}"'
|
||||
_err(f'unknown append variable: {variable}')
|
||||
|
||||
@@ -67,6 +67,9 @@ if(DEFINED BOARD_REVISION)
|
||||
set(BOARD_REVISION_CONFIG "${CMAKE_CURRENT_BINARY_DIR}/empty.conf")
|
||||
endif()
|
||||
|
||||
# Unset shield configuration files if set to prevent including in sysbuild
|
||||
set(shield_conf_files)
|
||||
|
||||
list(APPEND ZEPHYR_KCONFIG_MODULES_DIR BOARD=${BOARD})
|
||||
set(KCONFIG_NAMESPACE SB_CONFIG)
|
||||
|
||||
|
||||
@@ -130,6 +130,10 @@ config INIT_PLL1
|
||||
Note that flash programming operations are limited to 100MHz, and
|
||||
this PLL should not be used as the core clock in those cases.
|
||||
|
||||
config SYS_CLOCK_HW_CYCLES_PER_SEC
|
||||
default 144000000 if INIT_PLL1
|
||||
default 96000000
|
||||
|
||||
config SECOND_CORE_MCUX
|
||||
bool "LPC55xxx's second core"
|
||||
depends on HAS_MCUX
|
||||
|
||||
@@ -8505,7 +8505,7 @@ static void le_ltk_request(struct pdu_data *pdu_data, uint16_t handle,
|
||||
}
|
||||
|
||||
static void encrypt_change(uint8_t err, uint16_t handle,
|
||||
struct net_buf *buf)
|
||||
struct net_buf *buf, bool encryption_on)
|
||||
{
|
||||
struct bt_hci_evt_encrypt_change *ep;
|
||||
|
||||
@@ -8516,9 +8516,9 @@ static void encrypt_change(uint8_t err, uint16_t handle,
|
||||
hci_evt_create(buf, BT_HCI_EVT_ENCRYPT_CHANGE, sizeof(*ep));
|
||||
ep = net_buf_add(buf, sizeof(*ep));
|
||||
|
||||
ep->status = err;
|
||||
ep->status = err ? err : (encryption_on ? err : BT_HCI_ERR_UNSPECIFIED);
|
||||
ep->handle = sys_cpu_to_le16(handle);
|
||||
ep->encrypt = !err ? 1 : 0;
|
||||
ep->encrypt = encryption_on ? 1 : 0;
|
||||
}
|
||||
#endif /* CONFIG_BT_CTLR_LE_ENC */
|
||||
|
||||
@@ -8660,7 +8660,7 @@ static void encode_data_ctrl(struct node_rx_pdu *node_rx,
|
||||
break;
|
||||
|
||||
case PDU_DATA_LLCTRL_TYPE_START_ENC_RSP:
|
||||
encrypt_change(0x00, handle, buf);
|
||||
encrypt_change(0x00, handle, buf, true);
|
||||
break;
|
||||
#endif /* CONFIG_BT_CTLR_LE_ENC */
|
||||
|
||||
@@ -8677,7 +8677,7 @@ static void encode_data_ctrl(struct node_rx_pdu *node_rx,
|
||||
#if defined(CONFIG_BT_CTLR_LE_ENC)
|
||||
case PDU_DATA_LLCTRL_TYPE_REJECT_IND:
|
||||
encrypt_change(pdu_data->llctrl.reject_ind.error_code, handle,
|
||||
buf);
|
||||
buf, false);
|
||||
break;
|
||||
#endif /* CONFIG_BT_CTLR_LE_ENC */
|
||||
|
||||
|
||||
@@ -49,6 +49,9 @@
|
||||
|
||||
static int init_reset(void);
|
||||
static int prepare_cb(struct lll_prepare_param *p);
|
||||
#if !defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO)
|
||||
static void isr_early_abort(void *param);
|
||||
#endif /* !CONFIG_BT_TICKER_EXT_EXPIRE_INFO */
|
||||
static void isr_done(void *param);
|
||||
#if defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK)
|
||||
static void isr_tx_chain(void *param);
|
||||
@@ -188,7 +191,7 @@ static int prepare_cb(struct lll_prepare_param *p)
|
||||
|
||||
/* Abort if no aux_ptr filled */
|
||||
if (unlikely(!pri_hdr->aux_ptr || !PDU_ADV_AUX_PTR_OFFSET_GET(aux_ptr))) {
|
||||
radio_isr_set(lll_isr_early_abort, lll);
|
||||
radio_isr_set(isr_early_abort, lll);
|
||||
radio_disable();
|
||||
|
||||
return 0;
|
||||
@@ -325,7 +328,7 @@ static int prepare_cb(struct lll_prepare_param *p)
|
||||
if (overhead) {
|
||||
LL_ASSERT_OVERHEAD(overhead);
|
||||
|
||||
radio_isr_set(lll_isr_abort, lll);
|
||||
radio_isr_set(isr_done, lll);
|
||||
radio_disable();
|
||||
|
||||
return -ECANCELED;
|
||||
@@ -347,6 +350,33 @@ static int prepare_cb(struct lll_prepare_param *p)
|
||||
return 0;
|
||||
}
|
||||
|
||||
#if !defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO)
|
||||
static void isr_race(void *param)
|
||||
{
|
||||
radio_status_reset();
|
||||
}
|
||||
|
||||
static void isr_early_abort(void *param)
|
||||
{
|
||||
struct event_done_extra *extra;
|
||||
int err;
|
||||
|
||||
/* Generate auxiliary radio event done */
|
||||
extra = ull_done_extra_type_set(EVENT_DONE_EXTRA_TYPE_ADV_AUX);
|
||||
LL_ASSERT(extra);
|
||||
|
||||
radio_isr_set(isr_race, param);
|
||||
if (!radio_is_idle()) {
|
||||
radio_disable();
|
||||
}
|
||||
|
||||
err = lll_hfclock_off();
|
||||
LL_ASSERT(err >= 0);
|
||||
|
||||
lll_done(NULL);
|
||||
}
|
||||
#endif /* !CONFIG_BT_TICKER_EXT_EXPIRE_INFO */
|
||||
|
||||
static void isr_done(void *param)
|
||||
{
|
||||
struct event_done_extra *extra;
|
||||
|
||||
@@ -1951,12 +1951,15 @@ int ull_disable(void *lll)
|
||||
if (!ull_ref_get(hdr)) {
|
||||
return -EALREADY;
|
||||
}
|
||||
cpu_dmb(); /* Ensure synchronized data access */
|
||||
|
||||
k_sem_init(&sem, 0, 1);
|
||||
|
||||
hdr->disabled_param = &sem;
|
||||
hdr->disabled_cb = disabled_cb;
|
||||
|
||||
cpu_dmb(); /* Ensure synchronized data access */
|
||||
|
||||
/* ULL_HIGH can run after we have call `ull_ref_get` and it can
|
||||
* decrement the ref count. Hence, handle this race condition by
|
||||
* ensuring that `disabled_cb` has been set while the ref count is still
|
||||
|
||||
@@ -284,11 +284,26 @@ void llcp_rx_node_retain(struct proc_ctx *ctx)
|
||||
{
|
||||
LL_ASSERT(ctx->node_ref.rx);
|
||||
|
||||
/* Mark RX node to NOT release */
|
||||
ctx->node_ref.rx->hdr.type = NODE_RX_TYPE_RETAIN;
|
||||
/* Only retain if not already retained */
|
||||
if (ctx->node_ref.rx->hdr.type != NODE_RX_TYPE_RETAIN) {
|
||||
/* Mark RX node to NOT release */
|
||||
ctx->node_ref.rx->hdr.type = NODE_RX_TYPE_RETAIN;
|
||||
|
||||
/* store link element reference to use once this node is moved up */
|
||||
ctx->node_ref.rx->hdr.link = ctx->node_ref.link;
|
||||
/* store link element reference to use once this node is moved up */
|
||||
ctx->node_ref.rx->hdr.link = ctx->node_ref.link;
|
||||
}
|
||||
}
|
||||
|
||||
void llcp_rx_node_release(struct proc_ctx *ctx)
|
||||
{
|
||||
LL_ASSERT(ctx->node_ref.rx);
|
||||
|
||||
/* Only release if retained */
|
||||
if (ctx->node_ref.rx->hdr.type == NODE_RX_TYPE_RETAIN) {
|
||||
/* Mark RX node to release and release */
|
||||
ctx->node_ref.rx->hdr.type = NODE_RX_TYPE_RELEASE;
|
||||
ll_rx_put_sched(ctx->node_ref.rx->hdr.link, ctx->node_ref.rx);
|
||||
}
|
||||
}
|
||||
|
||||
void llcp_nodes_release(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
@@ -296,12 +311,14 @@ void llcp_nodes_release(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
if (ctx->node_ref.rx && ctx->node_ref.rx->hdr.type == NODE_RX_TYPE_RETAIN) {
|
||||
/* RX node retained, so release */
|
||||
ctx->node_ref.rx->hdr.link->mem = conn->llcp.rx_node_release;
|
||||
ctx->node_ref.rx->hdr.type = NODE_RX_TYPE_RELEASE;
|
||||
conn->llcp.rx_node_release = ctx->node_ref.rx;
|
||||
}
|
||||
#if defined(CONFIG_BT_CTLR_PHY) && defined(CONFIG_BT_CTLR_DATA_LENGTH)
|
||||
if (ctx->proc == PROC_PHY_UPDATE && ctx->data.pu.ntf_dle_node) {
|
||||
/* RX node retained, so release */
|
||||
ctx->data.pu.ntf_dle_node->hdr.link->mem = conn->llcp.rx_node_release;
|
||||
ctx->data.pu.ntf_dle_node->hdr.type = NODE_RX_TYPE_RELEASE;
|
||||
conn->llcp.rx_node_release = ctx->data.pu.ntf_dle_node;
|
||||
}
|
||||
#endif
|
||||
@@ -706,9 +723,6 @@ void ull_cp_release_nodes(struct ll_conn *conn)
|
||||
hdr = &rx->hdr;
|
||||
rx = hdr->link->mem;
|
||||
|
||||
/* Mark for buffer for release */
|
||||
hdr->type = NODE_RX_TYPE_RELEASE;
|
||||
|
||||
/* enqueue rx node towards Thread */
|
||||
ll_rx_put(hdr->link, hdr);
|
||||
}
|
||||
|
||||
@@ -1135,6 +1135,7 @@ static void rp_comm_ntf(struct ll_conn *conn, struct proc_ctx *ctx, uint8_t gene
|
||||
|
||||
/* Allocate ntf node */
|
||||
ntf = ctx->node_ref.rx;
|
||||
ctx->node_ref.rx = NULL;
|
||||
LL_ASSERT(ntf);
|
||||
|
||||
/* This should be an 'old' RX node, so put/sched when done */
|
||||
|
||||
@@ -196,6 +196,22 @@ static bool cu_check_conn_parameters(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
}
|
||||
#endif /* CONFIG_BT_CTLR_CONN_PARAM_REQ */
|
||||
|
||||
static bool cu_check_conn_ind_parameters(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
{
|
||||
const uint16_t interval_max = ctx->data.cu.interval_max; /* unit 1.25ms */
|
||||
const uint16_t timeout = ctx->data.cu.timeout; /* unit 10ms */
|
||||
const uint16_t latency = ctx->data.cu.latency;
|
||||
|
||||
/* Valid conn_update_ind parameters */
|
||||
return (interval_max >= CONN_INTERVAL_MIN(conn)) &&
|
||||
(interval_max <= CONN_UPDATE_CONN_INTV_4SEC) &&
|
||||
(latency <= CONN_UPDATE_LATENCY_MAX) &&
|
||||
(timeout >= CONN_UPDATE_TIMEOUT_100MS) &&
|
||||
(timeout <= CONN_UPDATE_TIMEOUT_32SEC) &&
|
||||
((timeout * 4U) > /* *4U re. conn events is equivalent to *2U re. ms */
|
||||
((latency + 1U) * interval_max));
|
||||
}
|
||||
|
||||
static void cu_prepare_update_ind(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
{
|
||||
ctx->data.cu.win_size = 1U;
|
||||
@@ -585,8 +601,20 @@ static void lp_cu_st_wait_rx_conn_update_ind(struct ll_conn *conn, struct proc_c
|
||||
switch (evt) {
|
||||
case LP_CU_EVT_CONN_UPDATE_IND:
|
||||
llcp_pdu_decode_conn_update_ind(ctx, param);
|
||||
|
||||
/* Invalid PDU, mark the connection for termination */
|
||||
if (!cu_check_conn_ind_parameters(conn, ctx)) {
|
||||
llcp_rr_set_incompat(conn, INCOMPAT_NO_COLLISION);
|
||||
conn->llcp_terminate.reason_final = BT_HCI_ERR_INVALID_LL_PARAM;
|
||||
lp_cu_complete(conn, ctx);
|
||||
break;
|
||||
}
|
||||
|
||||
llcp_rr_set_incompat(conn, INCOMPAT_RESERVED);
|
||||
|
||||
/* Keep RX node to use for NTF */
|
||||
llcp_rx_node_retain(ctx);
|
||||
|
||||
ctx->state = LP_CU_STATE_WAIT_INSTANT;
|
||||
break;
|
||||
case LP_CU_EVT_UNKNOWN:
|
||||
@@ -633,8 +661,7 @@ static void lp_cu_check_instant(struct ll_conn *conn, struct proc_ctx *ctx, uint
|
||||
lp_cu_ntf_complete(conn, ctx, evt, param);
|
||||
} else {
|
||||
/* Release RX node kept for NTF */
|
||||
ctx->node_ref.rx->hdr.type = NODE_RX_TYPE_RELEASE;
|
||||
ll_rx_put_sched(ctx->node_ref.rx->hdr.link, ctx->node_ref.rx);
|
||||
llcp_rx_node_release(ctx);
|
||||
ctx->node_ref.rx = NULL;
|
||||
|
||||
lp_cu_complete(conn, ctx);
|
||||
@@ -973,11 +1000,18 @@ static void rp_cu_st_wait_conn_param_req_available(struct ll_conn *conn, struct
|
||||
case RP_CU_EVT_RUN:
|
||||
if (cpr_active_is_set(conn)) {
|
||||
ctx->state = RP_CU_STATE_WAIT_CONN_PARAM_REQ_AVAILABLE;
|
||||
|
||||
if (!llcp_rr_ispaused(conn) && llcp_tx_alloc_peek(conn, ctx)) {
|
||||
/* We're good to reject immediately */
|
||||
ctx->data.cu.rejected_opcode = PDU_DATA_LLCTRL_TYPE_CONN_PARAM_REQ;
|
||||
ctx->data.cu.error = BT_HCI_ERR_UNSUPP_LL_PARAM_VAL;
|
||||
rp_cu_send_reject_ext_ind(conn, ctx, evt, param);
|
||||
|
||||
/* Possibly retained rx node to be released as we won't need it */
|
||||
llcp_rx_node_release(ctx);
|
||||
ctx->node_ref.rx = NULL;
|
||||
|
||||
break;
|
||||
}
|
||||
/* In case we have to defer NTF */
|
||||
llcp_rx_node_retain(ctx);
|
||||
@@ -992,6 +1026,9 @@ static void rp_cu_st_wait_conn_param_req_available(struct ll_conn *conn, struct
|
||||
rp_cu_conn_param_req_ntf(conn, ctx);
|
||||
ctx->state = RP_CU_STATE_WAIT_CONN_PARAM_REQ_REPLY;
|
||||
} else {
|
||||
/* Possibly retained rx node to be released as we won't need it */
|
||||
llcp_rx_node_release(ctx);
|
||||
ctx->node_ref.rx = NULL;
|
||||
#if defined(CONFIG_BT_CTLR_USER_CPR_ANCHOR_POINT_MOVE)
|
||||
/* Handle APM as a vendor specific user extension */
|
||||
if (conn->lll.role == BT_HCI_ROLE_PERIPHERAL &&
|
||||
@@ -1177,8 +1214,7 @@ static void rp_cu_check_instant(struct ll_conn *conn, struct proc_ctx *ctx, uint
|
||||
cu_ntf(conn, ctx);
|
||||
} else {
|
||||
/* Release RX node kept for NTF */
|
||||
ctx->node_ref.rx->hdr.type = NODE_RX_TYPE_RELEASE;
|
||||
ll_rx_put_sched(ctx->node_ref.rx->hdr.link, ctx->node_ref.rx);
|
||||
llcp_rx_node_release(ctx);
|
||||
ctx->node_ref.rx = NULL;
|
||||
}
|
||||
rp_cu_complete(conn, ctx);
|
||||
@@ -1198,19 +1234,27 @@ static void rp_cu_st_wait_rx_conn_update_ind(struct ll_conn *conn, struct proc_c
|
||||
case BT_HCI_ROLE_PERIPHERAL:
|
||||
llcp_pdu_decode_conn_update_ind(ctx, param);
|
||||
|
||||
if (is_instant_not_passed(ctx->data.cu.instant,
|
||||
ull_conn_event_counter(conn))) {
|
||||
/* Valid PDU */
|
||||
if (cu_check_conn_ind_parameters(conn, ctx)) {
|
||||
if (is_instant_not_passed(ctx->data.cu.instant,
|
||||
ull_conn_event_counter(conn))) {
|
||||
/* Keep RX node to use for NTF */
|
||||
llcp_rx_node_retain(ctx);
|
||||
|
||||
llcp_rx_node_retain(ctx);
|
||||
ctx->state = RP_CU_STATE_WAIT_INSTANT;
|
||||
|
||||
/* In case we only just received it in time */
|
||||
rp_cu_check_instant(conn, ctx, evt, param);
|
||||
break;
|
||||
}
|
||||
|
||||
ctx->state = RP_CU_STATE_WAIT_INSTANT;
|
||||
/* In case we only just received it in time */
|
||||
rp_cu_check_instant(conn, ctx, evt, param);
|
||||
} else {
|
||||
conn->llcp_terminate.reason_final = BT_HCI_ERR_INSTANT_PASSED;
|
||||
llcp_rr_complete(conn);
|
||||
ctx->state = RP_CU_STATE_IDLE;
|
||||
} else {
|
||||
conn->llcp_terminate.reason_final = BT_HCI_ERR_INVALID_LL_PARAM;
|
||||
}
|
||||
|
||||
llcp_rr_complete(conn);
|
||||
ctx->state = RP_CU_STATE_IDLE;
|
||||
break;
|
||||
default:
|
||||
/* Unknown role */
|
||||
|
||||
@@ -225,6 +225,7 @@ static void lp_enc_ntf(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
|
||||
/* Piggy-back on RX node */
|
||||
ntf = ctx->node_ref.rx;
|
||||
ctx->node_ref.rx = NULL;
|
||||
LL_ASSERT(ntf);
|
||||
|
||||
ntf->hdr.type = NODE_RX_TYPE_DC_PDU;
|
||||
@@ -381,19 +382,29 @@ static void lp_enc_store_s(struct ll_conn *conn, struct proc_ctx *ctx, struct pd
|
||||
|
||||
static inline uint8_t reject_error_code(struct pdu_data *pdu)
|
||||
{
|
||||
uint8_t error;
|
||||
|
||||
if (pdu->llctrl.opcode == PDU_DATA_LLCTRL_TYPE_REJECT_IND) {
|
||||
return pdu->llctrl.reject_ind.error_code;
|
||||
error = pdu->llctrl.reject_ind.error_code;
|
||||
#if defined(CONFIG_BT_CTLR_EXT_REJ_IND)
|
||||
} else if (pdu->llctrl.opcode == PDU_DATA_LLCTRL_TYPE_REJECT_EXT_IND) {
|
||||
return pdu->llctrl.reject_ext_ind.error_code;
|
||||
error = pdu->llctrl.reject_ext_ind.error_code;
|
||||
#endif /* CONFIG_BT_CTLR_EXT_REJ_IND */
|
||||
} else {
|
||||
/* Called with an invalid PDU */
|
||||
LL_ASSERT(0);
|
||||
|
||||
/* Keep compiler happy */
|
||||
return BT_HCI_ERR_UNSPECIFIED;
|
||||
error = BT_HCI_ERR_UNSPECIFIED;
|
||||
}
|
||||
|
||||
/* Check expected error code from the peer */
|
||||
if (error != BT_HCI_ERR_PIN_OR_KEY_MISSING &&
|
||||
error != BT_HCI_ERR_UNSUPP_REMOTE_FEATURE) {
|
||||
error = BT_HCI_ERR_UNSPECIFIED;
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
static void lp_enc_st_wait_rx_enc_rsp(struct ll_conn *conn, struct proc_ctx *ctx, uint8_t evt,
|
||||
|
||||
@@ -413,6 +413,7 @@ void llcp_ntf_set_pending(struct ll_conn *conn);
|
||||
void llcp_ntf_clear_pending(struct ll_conn *conn);
|
||||
bool llcp_ntf_pending(struct ll_conn *conn);
|
||||
void llcp_rx_node_retain(struct proc_ctx *ctx);
|
||||
void llcp_rx_node_release(struct proc_ctx *ctx);
|
||||
|
||||
/*
|
||||
* ULL -> LLL Interface
|
||||
|
||||
@@ -81,6 +81,12 @@ void llcp_lr_check_done(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
ctx_header = llcp_lr_peek(conn);
|
||||
LL_ASSERT(ctx_header == ctx);
|
||||
|
||||
/* If we have a node rx it must not be marked RETAIN as
|
||||
* the memory referenced would leak
|
||||
*/
|
||||
LL_ASSERT(ctx->node_ref.rx == NULL ||
|
||||
ctx->node_ref.rx->hdr.type != NODE_RX_TYPE_RETAIN);
|
||||
|
||||
lr_dequeue(conn);
|
||||
|
||||
llcp_proc_ctx_release(ctx);
|
||||
@@ -312,6 +318,11 @@ void llcp_lr_rx(struct ll_conn *conn, struct proc_ctx *ctx, memq_link_t *link,
|
||||
break;
|
||||
}
|
||||
|
||||
/* If rx node was not retained clear reference */
|
||||
if (ctx->node_ref.rx && ctx->node_ref.rx->hdr.type != NODE_RX_TYPE_RETAIN) {
|
||||
ctx->node_ref.rx = NULL;
|
||||
}
|
||||
|
||||
llcp_lr_check_done(conn, ctx);
|
||||
}
|
||||
|
||||
|
||||
@@ -433,6 +433,7 @@ static void pu_ntf(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
|
||||
/* Piggy-back on stored RX node */
|
||||
ntf = ctx->node_ref.rx;
|
||||
ctx->node_ref.rx = NULL;
|
||||
LL_ASSERT(ntf);
|
||||
|
||||
if (ctx->data.pu.ntf_pu) {
|
||||
@@ -449,15 +450,9 @@ static void pu_ntf(struct ll_conn *conn, struct proc_ctx *ctx)
|
||||
}
|
||||
|
||||
/* Enqueue notification towards LL */
|
||||
#if defined(CONFIG_BT_CTLR_DATA_LENGTH)
|
||||
/* only 'put' as the 'sched' is handled when handling DLE ntf */
|
||||
ll_rx_put(ntf->hdr.link, ntf);
|
||||
#else
|
||||
ll_rx_put_sched(ntf->hdr.link, ntf);
|
||||
#endif /* CONFIG_BT_CTLR_DATA_LENGTH */
|
||||
|
||||
ctx->data.pu.ntf_pu = 0;
|
||||
ctx->node_ref.rx = NULL;
|
||||
}
|
||||
|
||||
#if defined(CONFIG_BT_CTLR_DATA_LENGTH)
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user