Skip to content

Commit 5fd2948

Browse files
committed
tests: add tests for errors related to adding keys
These are ported from the libkeyutils test suite (tests/keyctl/add/bad-args).
1 parent 61268e1 commit 5fd2948

File tree

4 files changed

+213
-0
lines changed

4 files changed

+213
-0
lines changed

src/tests/add.rs

+117
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,117 @@
1+
// Copyright (c) 2019, Ben Boeckel
2+
// All rights reserved.
3+
//
4+
// Redistribution and use in source and binary forms, with or without modification,
5+
// are permitted provided that the following conditions are met:
6+
//
7+
// * Redistributions of source code must retain the above copyright notice,
8+
// this list of conditions and the following disclaimer.
9+
// * Redistributions in binary form must reproduce the above copyright notice,
10+
// this list of conditions and the following disclaimer in the documentation
11+
// and/or other materials provided with the distribution.
12+
// * Neither the name of this project nor the names of its contributors
13+
// may be used to endorse or promote products derived from this software
14+
// without specific prior written permission.
15+
//
16+
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17+
// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18+
// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19+
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
20+
// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21+
// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22+
// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
23+
// ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24+
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25+
// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26+
27+
use std::iter;
28+
29+
use crate::keytypes::User;
30+
use crate::{Keyring, KeyringSerial, SpecialKeyring};
31+
32+
use super::utils::kernel::*;
33+
use super::utils::keys::*;
34+
35+
#[test]
36+
fn empty_key_type() {
37+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
38+
let err = keyring.add_key::<EmptyKey, _, _>("", ()).unwrap_err();
39+
assert_eq!(err, errno::Errno(libc::EINVAL));
40+
}
41+
42+
#[test]
43+
fn unsupported_key_type() {
44+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
45+
let err = keyring.add_key::<UnsupportedKey, _, _>("", ()).unwrap_err();
46+
assert_eq!(err, errno::Errno(libc::ENODEV));
47+
}
48+
49+
#[test]
50+
fn invalid_key_type() {
51+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
52+
let err = keyring.add_key::<InvalidKey, _, _>("", ()).unwrap_err();
53+
assert_eq!(err, errno::Errno(libc::EPERM));
54+
}
55+
56+
#[test]
57+
fn maxlen_key_type() {
58+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
59+
let err = keyring.add_key::<MaxLenKey, _, _>("", ()).unwrap_err();
60+
assert_eq!(err, errno::Errno(libc::ENODEV));
61+
}
62+
63+
#[test]
64+
fn overlong_key_type() {
65+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
66+
let err = keyring.add_key::<OverlongKey, _, _>("", ()).unwrap_err();
67+
assert_eq!(err, errno::Errno(libc::EINVAL));
68+
}
69+
70+
#[test]
71+
fn keyring_with_payload() {
72+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
73+
let err = keyring
74+
.add_key::<KeyringShadow, _, _>("", "payload")
75+
.unwrap_err();
76+
assert_eq!(err, errno::Errno(libc::EINVAL));
77+
}
78+
79+
#[test]
80+
fn max_user_description() {
81+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
82+
// Subtract one because the NUL is added in the kernel API.
83+
let maxdesc: String = iter::repeat('a').take(*PAGE_SIZE - 1).collect();
84+
let res = keyring.add_key::<User, _, _>(maxdesc.as_ref(), "payload".as_bytes());
85+
// If the user's quota is smaller than this, it's an error.
86+
if KEY_INFO.maxbytes < *PAGE_SIZE {
87+
assert_eq!(res.unwrap_err(), errno::Errno(libc::EDQUOT));
88+
} else {
89+
let key = res.unwrap();
90+
assert_eq!(key.description().unwrap().description, maxdesc);
91+
key.invalidate().unwrap();
92+
}
93+
}
94+
95+
#[test]
96+
fn overlong_user_description() {
97+
let mut keyring = Keyring::attach_or_create(SpecialKeyring::Process).unwrap();
98+
// On MIPS with < 3.19, there is a bug where this is allowed. 3.19 was released in Feb 2015,
99+
// so this is being ignored here.
100+
let toolarge: String = iter::repeat('a').take(*PAGE_SIZE).collect();
101+
let err = keyring
102+
.add_key::<User, _, _>(toolarge.as_ref(), "payload".as_bytes())
103+
.unwrap_err();
104+
assert_eq!(err, errno::Errno(libc::EINVAL));
105+
}
106+
107+
#[test]
108+
fn invalid_keyring() {
109+
// Yes, we're explicitly breaking the NonZeroI32 rules here. However, it is not passing
110+
// through any bits which care (e.g., `Option`), so this is purely to test that using an
111+
// invalid keyring ID gives back `EINVAL` as expected.
112+
let mut keyring = unsafe { Keyring::new(KeyringSerial::new_unchecked(0)) };
113+
let err = keyring
114+
.add_key::<User, _, _>("desc", "payload".as_bytes())
115+
.unwrap_err();
116+
assert_eq!(err, errno::Errno(libc::EINVAL));
117+
}

src/tests/mod.rs

+2
Original file line numberDiff line numberDiff line change
@@ -27,3 +27,5 @@
2727
//! The test structure here comes from the structure in libkeyutils.
2828
2929
mod utils;
30+
31+
mod add;

src/tests/utils/keys.rs

+93
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,93 @@
1+
// Copyright (c) 2019, Ben Boeckel
2+
// All rights reserved.
3+
//
4+
// Redistribution and use in source and binary forms, with or without modification,
5+
// are permitted provided that the following conditions are met:
6+
//
7+
// * Redistributions of source code must retain the above copyright notice,
8+
// this list of conditions and the following disclaimer.
9+
// * Redistributions in binary form must reproduce the above copyright notice,
10+
// this list of conditions and the following disclaimer in the documentation
11+
// and/or other materials provided with the distribution.
12+
// * Neither the name of this project nor the names of its contributors
13+
// may be used to endorse or promote products derived from this software
14+
// without specific prior written permission.
15+
//
16+
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
17+
// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18+
// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19+
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
20+
// ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21+
// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22+
// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
23+
// ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24+
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25+
// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26+
27+
use crate::KeyType;
28+
29+
pub struct EmptyKey;
30+
31+
impl KeyType for EmptyKey {
32+
type Description = str;
33+
type Payload = ();
34+
35+
fn name() -> &'static str {
36+
""
37+
}
38+
}
39+
40+
pub struct UnsupportedKey;
41+
42+
impl KeyType for UnsupportedKey {
43+
type Description = str;
44+
type Payload = ();
45+
46+
fn name() -> &'static str {
47+
"unsupported_key_type"
48+
}
49+
}
50+
51+
pub struct InvalidKey;
52+
53+
impl KeyType for InvalidKey {
54+
type Description = str;
55+
type Payload = ();
56+
57+
fn name() -> &'static str {
58+
".invalid_key_type"
59+
}
60+
}
61+
62+
pub struct MaxLenKey;
63+
64+
impl KeyType for MaxLenKey {
65+
type Description = str;
66+
type Payload = ();
67+
68+
fn name() -> &'static str {
69+
"1234567890123456789012345678901"
70+
}
71+
}
72+
73+
pub struct OverlongKey;
74+
75+
impl KeyType for OverlongKey {
76+
type Description = str;
77+
type Payload = ();
78+
79+
fn name() -> &'static str {
80+
"12345678901234567890123456789012"
81+
}
82+
}
83+
84+
pub struct KeyringShadow;
85+
86+
impl KeyType for KeyringShadow {
87+
type Description = str;
88+
type Payload = str;
89+
90+
fn name() -> &'static str {
91+
"keyring"
92+
}
93+
}

src/tests/utils/mod.rs

+1
Original file line numberDiff line numberDiff line change
@@ -25,3 +25,4 @@
2525
// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2626

2727
pub mod kernel;
28+
pub mod keys;

0 commit comments

Comments
 (0)