Skip to content

Commit

Permalink
Be a better daemon by becoming a session leader and redirecting stand…
Browse files Browse the repository at this point in the history
…ard streams.
  • Loading branch information
Soft committed Mar 25, 2018
1 parent e6c77cb commit a0a5a0d
Show file tree
Hide file tree
Showing 5 changed files with 32 additions and 4 deletions.
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ failure = "0.1.1"
nom = "3.2.1"
clap = "2.31.2"
nix = "0.10.0"
libc = "0.2.39"

[build-dependencies]
clap = "2.31.2"
Expand Down
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -71,15 +71,15 @@ The output format can be changed using the `-f FORMAT` switch. The possible
format values are listed bellow:

| Format Specifier | Description | Example | Custom Format Equivalent |
| ---------------- | --------------------------------- | --------------------- | ------------------------ |
| ---------------- | ----------------------------------------- | --------------------- | ------------------------ |
| `hex` | Lowercase hexadecimal (default) | `#ff00ff` | `#%{02hr}%{02hg}%{02hb}` |
| `HEX` | Uppercase hexadecimal | `#00FF00` | `#%{02Hr}%{02Hg}%{02Hb}` |
| `hex!` | Compact lowercase hexadecimal<sup>1</sup> | `#fff` | Not expressible |
| `HEX!` | Compact uppercase hexadecimal<sup>1</sup> | `#F0F` | Not expressible |
| `rgb` | Decimal RGB | `rgb(255, 255, 255)` | `rgb(%{r}, %{g}, %{b})` |
| `plain` | Decimal with semicolon separators | `0;0;0` | `%{r};%{g};%{b}` |

**1:** The compact form refers to CSS three-letter color codes as specified by [CSS
**1**: The compact form refers to CSS three-letter color codes as specified by [CSS
Color Module Level 3](https://www.w3.org/TR/2018/PR-css-color-3-20180315/#rgb-color).
If the color is not expressible in three-letter form, the regular six-letter
form will be used.
Expand Down
1 change: 1 addition & 0 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ extern crate xcb;
extern crate failure;
extern crate clap;
extern crate nix;
extern crate libc;
#[macro_use]
extern crate nom;

Expand Down
29 changes: 27 additions & 2 deletions src/selection.rs
Original file line number Diff line number Diff line change
@@ -1,17 +1,30 @@
use std;
use std::fs;
use std::str::FromStr;
use std::os::unix::io::IntoRawFd;
use failure::{Error, err_msg};
use nix::unistd::{fork, ForkResult};
use nix::unistd::{self, fork, ForkResult};
use xcb::base as xbase;
use xcb::base::Connection;
use xcb::xproto;
use libc;

pub fn into_daemon() -> Result<ForkResult, Error> {
match fork()? {
parent@ForkResult::Parent { .. } => Ok(parent),
child@ForkResult::Child => {
unistd::setsid()?;
std::env::set_current_dir("/")?;
// TODO: Point file handles to /dev/null
// Not sure if this is safe...
let dev_null = fs::OpenOptions::new()
.read(true)
.write(true)
.open("/dev/null")?
.into_raw_fd();
for fd in &[libc::STDIN_FILENO, libc::STDOUT_FILENO, libc::STDERR_FILENO] {
unistd::close(*fd)?;
unistd::dup2(dev_null, *fd)?;
}
Ok(child)
}
}
Expand Down Expand Up @@ -45,6 +58,15 @@ impl Selection {
}
}

// The selection daemon presented here is not a perfect implementation of the
// ICCCM recommendation. Currently, it does not support large transfers and does
// not verify that the requestor has received the data by monitoring for atom
// deletion. Additionally, we do not support MULTIPLE and TIMESTAMP targets even
// though those are required by the spec. However, this implements just enough
// of the spec to work well enough in practice as color codes do not tend to be
// that large. However, this assumption could of course fail with custom
// templates.

pub fn set_selection(conn: &Connection,
root: xproto::Window,
selection: Selection,
Expand All @@ -68,6 +90,7 @@ pub fn set_selection(conn: &Connection,
&[])
.request_check()?;

// It would be better to use a real timestamp
xproto::set_selection_owner(conn, window, selection, xbase::CURRENT_TIME)
.request_check()?;

Expand All @@ -83,6 +106,8 @@ pub fn set_selection(conn: &Connection,
let event: &xproto::SelectionRequestEvent= unsafe {
xbase::cast_event(&event)
};

// We should check the event timestamp

let target = event.target();
let property = if target == utf8_string {
Expand Down

0 comments on commit a0a5a0d

Please sign in to comment.