feat(apps): permission manager equips apps (manifest+consent+decisions in /system), launches via init w/ file grant; shell unprivileged (/home); install/apps/allow/revoke; revoke stops running app; app-image tool; counter app

This commit is contained in:
2026-10-27 22:56:44 +01:00
parent 9bc31a9bbe
commit 90e11eb2e8
51 changed files with 1766 additions and 644 deletions

View File

@@ -0,0 +1,14 @@
[package]
name = "counter"
version = "0.1.0"
edition = "2024"
[[bin]]
name = "counter"
test = false
bench = false
[dependencies]
types = { workspace = true }
libkos = { workspace = true }

View File

@@ -0,0 +1,10 @@
# Remembers how often it ran, if the owner lets it keep a file.
[app]
id = "kos.counter"
name = "Counter"
version = "1.0.0"
binary = "counter"
author = "K-OS"
[capabilities]
optional = ["storage"]

View File

@@ -0,0 +1,59 @@
//! Counts its runs in its own data folder: the `storage` capability, which
//! it can do without (then it remembers nothing).
#![no_std]
#![forbid(unsafe_code)]
#![no_main]
extern crate libkos;
use libkos::fs::Storage;
use libkos::println;
use types::address::VirtualAddress;
const DATA_BUF_VA: VirtualAddress = VirtualAddress::from_raw(0x0180_0000);
const COUNT: &[u8] = b"count";
/// The number in the file, 0 if there is none yet.
fn read_count(fs: &mut Storage) -> u64 {
let Ok(h) = fs.open(COUNT) else { return 0 };
let mut buf = [0u8; 20];
let n = fs.read(h, &mut buf).unwrap_or(0);
let _ = fs.close(h);
core::str::from_utf8(&buf[..n]).ok().and_then(|s| s.trim().parse().ok()).unwrap_or(0)
}
fn write_count(fs: &mut Storage, count: u64) -> bool {
let mut digits = [0u8; 20];
let mut n = 0;
let mut v = count;
loop {
digits[n] = b'0' + (v % 10) as u8;
n += 1;
v /= 10;
if v == 0 {
break;
}
}
digits[..n].reverse();
let _ = fs.delete(COUNT);
let Ok(h) = fs.create(COUNT) else { return false };
let ok = fs.write(h, &digits[..n]) == Ok(n);
let _ = fs.close(h);
ok
}
fn main() {
let Some(mut fs) = libkos::start::data().and_then(|d| Storage::attach(d, DATA_BUF_VA).ok()) else {
println!("counter: not allowed to keep anything, so this is run 1 as far as it knows");
return;
};
let count = read_count(&mut fs) + 1;
if write_count(&mut fs, count) {
println!("counter: run {} (kept in its own data folder)", count);
} else {
println!("counter: run {}, but it could not save that", count);
}
}
libkos::entry!(main);