2021-01-17 13:58:43 +00:00
|
|
|
#+SETUPFILE: ~/.emacs.d/org-templates/projects.org
|
2020-04-06 07:06:14 +00:00
|
|
|
#+EXPORT_FILE_NAME: index
|
2021-01-17 13:58:43 +00:00
|
|
|
#+OPTIONS: toc:2
|
2020-04-06 07:06:14 +00:00
|
|
|
#+TITLE: Lynx
|
|
|
|
|
2020-04-15 13:44:16 +00:00
|
|
|
Lynx is a simple /unveil/ & /pledge/ wrapper. It returns /nil/ on unsupported systems,
|
|
|
|
currently only /OpenBSD/ is supported.
|
2020-04-06 07:06:14 +00:00
|
|
|
|
|
|
|
| Project Home | [[https://andinus.nand.sh/lynx][Lynx]] |
|
2020-05-01 23:55:42 +00:00
|
|
|
| Source Code | [[https://git.tilde.institute/andinus/lynx][Andinus / Lynx]] |
|
2020-04-06 07:06:14 +00:00
|
|
|
| GitHub (Mirror) | [[https://github.com/andinus/lynx][Lynx - GitHub]] |
|
|
|
|
|
2020-04-15 14:53:20 +00:00
|
|
|
* Why use lynx?
|
|
|
|
- *UnveilPaths* & *UnveilCommands*: /unix/ package provides simple Unveil syscalls so
|
|
|
|
this is useful because you don't have to write these functions yourself
|
|
|
|
manually in every project.
|
|
|
|
|
|
|
|
- /lynx/ manages build flags for you, which means that /lynx/ will return nil on
|
|
|
|
unsupported systems whereas you have handle that yourself in /unix/ package.
|
|
|
|
|
|
|
|
*Note*: Unveil, UnveilPaths & UnveilCommands ignore some errors, look at examples
|
|
|
|
before using them.
|
2020-04-06 07:06:14 +00:00
|
|
|
* Examples
|
2020-04-15 14:34:02 +00:00
|
|
|
** UnveilPaths / UnveilPathsStrict
|
|
|
|
UnveilPaths takes a map of path, permission & unveils them one by one, it will
|
|
|
|
return an error if unveil fails at any step. "no such file or directory" error
|
|
|
|
is ignored, if you want to get that error too then use UnveilPathsStrict.
|
2020-04-15 13:50:22 +00:00
|
|
|
|
|
|
|
#+BEGIN_SRC go
|
|
|
|
package main
|
|
|
|
|
2020-05-01 23:55:42 +00:00
|
|
|
import "git.tilde.institute/andinus/lynx"
|
2020-04-15 13:50:22 +00:00
|
|
|
|
|
|
|
func main() {
|
2020-04-15 14:34:02 +00:00
|
|
|
paths := make(map[string]string)
|
2020-04-15 13:50:22 +00:00
|
|
|
|
2020-04-15 14:34:02 +00:00
|
|
|
paths["/home"] = "r"
|
|
|
|
paths["/dev/null"] = "rw"
|
|
|
|
paths["/etc/examples"] = "rwc"
|
|
|
|
paths["/root"] = "rwcx"
|
|
|
|
|
|
|
|
err = lynx.UnveilPaths(paths)
|
2020-04-15 13:50:22 +00:00
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
// This will return an error if the path doesn't exist.
|
2020-04-15 14:34:02 +00:00
|
|
|
err = lynx.UnveilPathsStrict(paths)
|
2020-04-15 13:50:22 +00:00
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
#+END_SRC
|
2020-04-06 07:06:14 +00:00
|
|
|
** UnveilCommands
|
|
|
|
UnveilCommands takes a slice of commands & unveils them one by one, it will
|
|
|
|
return an error if unveil fails at any step. "no such file or directory" error
|
|
|
|
is ignored because binaries are not placed in every PATH.
|
|
|
|
|
|
|
|
Default permission is "rx".
|
|
|
|
|
|
|
|
#+BEGIN_SRC go
|
|
|
|
package main
|
|
|
|
|
2020-05-01 23:55:42 +00:00
|
|
|
import "git.tilde.institute/andinus/lynx"
|
2020-04-06 07:06:14 +00:00
|
|
|
|
|
|
|
func main() {
|
|
|
|
commands := []string{"cd", "ls", "rm"}
|
|
|
|
|
|
|
|
err = lynx.UnveilCommands(commands)
|
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
#+END_SRC
|
2020-04-15 14:34:02 +00:00
|
|
|
** UnveilBlock
|
|
|
|
UnveilBlock is just a wrapper around unix.UnveilBlock, it does nothing extra.
|
|
|
|
You should use unix.UnveilBlock.
|
2020-04-06 07:06:14 +00:00
|
|
|
|
|
|
|
#+BEGIN_SRC go
|
|
|
|
package main
|
|
|
|
|
2020-05-01 23:55:42 +00:00
|
|
|
import "git.tilde.institute/andinus/lynx"
|
2020-04-06 07:06:14 +00:00
|
|
|
|
|
|
|
func main() {
|
2020-04-15 14:34:02 +00:00
|
|
|
// Block further unveil calls.
|
|
|
|
err = lynx.UnveilBlock()
|
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
#+END_SRC
|
|
|
|
** Unveil / UnveilStrict
|
|
|
|
Unveil takes a path, permission & unveils it, it will return an error if unveil
|
|
|
|
fails at any step. "no such file or directory" error is ignored, if you want to
|
|
|
|
get that error too then use UnveilStrict.
|
2020-04-06 07:06:14 +00:00
|
|
|
|
2020-04-15 14:34:02 +00:00
|
|
|
#+BEGIN_SRC go
|
|
|
|
package main
|
2020-04-06 07:06:14 +00:00
|
|
|
|
2020-05-01 23:55:42 +00:00
|
|
|
import "git.tilde.institute/andinus/lynx"
|
2020-04-15 14:34:02 +00:00
|
|
|
|
|
|
|
func main() {
|
|
|
|
path := "/dev/null"
|
|
|
|
flags := "rw"
|
|
|
|
|
|
|
|
err = lynx.Unveil(path, flags)
|
2020-04-06 07:06:14 +00:00
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
// This will return an error if the path doesn't exist.
|
2020-04-15 14:34:02 +00:00
|
|
|
err = lynx.UnveilStrict(path, flags)
|
2020-04-06 07:06:14 +00:00
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
#+END_SRC
|
2020-04-15 14:34:02 +00:00
|
|
|
** Pledge / PledgePromises / PledgeExecpromises
|
|
|
|
These are simple wrappers to unix package functions. They add nothing extra, you
|
|
|
|
could simply change lynx.Pledge to unix.Pledge & it would just work.
|
2020-04-14 18:56:43 +00:00
|
|
|
|
|
|
|
#+BEGIN_SRC go
|
|
|
|
package main
|
|
|
|
|
2020-05-01 23:55:42 +00:00
|
|
|
import "git.tilde.institute/andinus/lynx"
|
2020-04-14 18:56:43 +00:00
|
|
|
|
|
|
|
func main() {
|
2020-04-15 14:34:02 +00:00
|
|
|
promises := "stdio unveil"
|
|
|
|
execpromises := "stdio"
|
|
|
|
|
|
|
|
err = lynx.Pledge(promises, execpromises)
|
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
// Drop promises.
|
|
|
|
promises = "stdio"
|
|
|
|
err = lynx.PledgePromises(promises)
|
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
// Drop execpromises.
|
|
|
|
execpromises = ""
|
|
|
|
err = lynx.PledgeExecpromises(execpromises)
|
2020-04-14 18:56:43 +00:00
|
|
|
if err != nil {
|
|
|
|
log.Fatal(err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
#+END_SRC
|