https://github.com/torvalds/linux
Revision ca10b9e9a8ca7342ee07065289cbe74ac128c169 authored by Eric Dumazet on 08 April 2013, 17:58:11 UTC, committed by David S. Miller on 09 April 2013, 17:23:11 UTC
Commit 90ba9b1986b5ac (tcp: tcp_make_synack() can use alloc_skb())
broke certain SELinux/NetLabel configurations by no longer correctly
assigning the sock to the outgoing SYNACK packet.

Cost of atomic operations on the LISTEN socket is quite big,
and we would like it to happen only if really needed.

This patch introduces a new security_ops->skb_owned_by() method,
that is a void operation unless selinux is active.

Reported-by: Miroslav Vadkerti <mvadkert@redhat.com>
Diagnosed-by: Paul Moore <pmoore@redhat.com>
Signed-off-by: Eric Dumazet <edumazet@google.com>
Cc: "David S. Miller" <davem@davemloft.net>
Cc: linux-security-module@vger.kernel.org
Acked-by: James Morris <james.l.morris@oracle.com>
Tested-by: Paul Moore <pmoore@redhat.com>
Acked-by: Paul Moore <pmoore@redhat.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
1 parent c802d75
Raw File
Tip revision: ca10b9e9a8ca7342ee07065289cbe74ac128c169 authored by Eric Dumazet on 08 April 2013, 17:58:11 UTC
selinux: add a skb_owned_by() hook
Tip revision: ca10b9e
atomic64_test.c
/*
 * Testsuite for atomic64_t functions
 *
 * Copyright © 2010  Luca Barbieri
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 */
#include <linux/init.h>
#include <linux/bug.h>
#include <linux/kernel.h>
#include <linux/atomic.h>

#define INIT(c) do { atomic64_set(&v, c); r = c; } while (0)
static __init int test_atomic64(void)
{
	long long v0 = 0xaaa31337c001d00dLL;
	long long v1 = 0xdeadbeefdeafcafeLL;
	long long v2 = 0xfaceabadf00df001LL;
	long long onestwos = 0x1111111122222222LL;
	long long one = 1LL;

	atomic64_t v = ATOMIC64_INIT(v0);
	long long r = v0;
	BUG_ON(v.counter != r);

	atomic64_set(&v, v1);
	r = v1;
	BUG_ON(v.counter != r);
	BUG_ON(atomic64_read(&v) != r);

	INIT(v0);
	atomic64_add(onestwos, &v);
	r += onestwos;
	BUG_ON(v.counter != r);

	INIT(v0);
	atomic64_add(-one, &v);
	r += -one;
	BUG_ON(v.counter != r);

	INIT(v0);
	r += onestwos;
	BUG_ON(atomic64_add_return(onestwos, &v) != r);
	BUG_ON(v.counter != r);

	INIT(v0);
	r += -one;
	BUG_ON(atomic64_add_return(-one, &v) != r);
	BUG_ON(v.counter != r);

	INIT(v0);
	atomic64_sub(onestwos, &v);
	r -= onestwos;
	BUG_ON(v.counter != r);

	INIT(v0);
	atomic64_sub(-one, &v);
	r -= -one;
	BUG_ON(v.counter != r);

	INIT(v0);
	r -= onestwos;
	BUG_ON(atomic64_sub_return(onestwos, &v) != r);
	BUG_ON(v.counter != r);

	INIT(v0);
	r -= -one;
	BUG_ON(atomic64_sub_return(-one, &v) != r);
	BUG_ON(v.counter != r);

	INIT(v0);
	atomic64_inc(&v);
	r += one;
	BUG_ON(v.counter != r);

	INIT(v0);
	r += one;
	BUG_ON(atomic64_inc_return(&v) != r);
	BUG_ON(v.counter != r);

	INIT(v0);
	atomic64_dec(&v);
	r -= one;
	BUG_ON(v.counter != r);

	INIT(v0);
	r -= one;
	BUG_ON(atomic64_dec_return(&v) != r);
	BUG_ON(v.counter != r);

	INIT(v0);
	BUG_ON(atomic64_xchg(&v, v1) != v0);
	r = v1;
	BUG_ON(v.counter != r);

	INIT(v0);
	BUG_ON(atomic64_cmpxchg(&v, v0, v1) != v0);
	r = v1;
	BUG_ON(v.counter != r);

	INIT(v0);
	BUG_ON(atomic64_cmpxchg(&v, v2, v1) != v0);
	BUG_ON(v.counter != r);

	INIT(v0);
	BUG_ON(atomic64_add_unless(&v, one, v0));
	BUG_ON(v.counter != r);

	INIT(v0);
	BUG_ON(!atomic64_add_unless(&v, one, v1));
	r += one;
	BUG_ON(v.counter != r);

#ifdef CONFIG_ARCH_HAS_ATOMIC64_DEC_IF_POSITIVE
	INIT(onestwos);
	BUG_ON(atomic64_dec_if_positive(&v) != (onestwos - 1));
	r -= one;
	BUG_ON(v.counter != r);

	INIT(0);
	BUG_ON(atomic64_dec_if_positive(&v) != -one);
	BUG_ON(v.counter != r);

	INIT(-one);
	BUG_ON(atomic64_dec_if_positive(&v) != (-one - one));
	BUG_ON(v.counter != r);
#else
#warning Please implement atomic64_dec_if_positive for your architecture and select the above Kconfig symbol
#endif

	INIT(onestwos);
	BUG_ON(!atomic64_inc_not_zero(&v));
	r += one;
	BUG_ON(v.counter != r);

	INIT(0);
	BUG_ON(atomic64_inc_not_zero(&v));
	BUG_ON(v.counter != r);

	INIT(-one);
	BUG_ON(!atomic64_inc_not_zero(&v));
	r += one;
	BUG_ON(v.counter != r);

#ifdef CONFIG_X86
	printk(KERN_INFO "atomic64 test passed for %s platform %s CX8 and %s SSE\n",
#ifdef CONFIG_X86_64
	       "x86-64",
#elif defined(CONFIG_X86_CMPXCHG64)
	       "i586+",
#else
	       "i386+",
#endif
	       boot_cpu_has(X86_FEATURE_CX8) ? "with" : "without",
	       boot_cpu_has(X86_FEATURE_XMM) ? "with" : "without");
#else
	printk(KERN_INFO "atomic64 test passed\n");
#endif

	return 0;
}

core_initcall(test_atomic64);
back to top