linux/include/net/scm.h
<<
>>
Prefs
   1#ifndef __LINUX_NET_SCM_H
   2#define __LINUX_NET_SCM_H
   3
   4#include <linux/limits.h>
   5#include <linux/net.h>
   6#include <linux/security.h>
   7#include <linux/pid.h>
   8#include <linux/nsproxy.h>
   9
  10/* Well, we should have at least one descriptor open
  11 * to accept passed FDs 8)
  12 */
  13#define SCM_MAX_FD      253
  14
  15struct scm_fp_list {
  16        short                   count;
  17        short                   max;
  18        struct file             *fp[SCM_MAX_FD];
  19};
  20
  21struct scm_cookie {
  22        struct pid              *pid;           /* Skb credentials */
  23        const struct cred       *cred;
  24        struct scm_fp_list      *fp;            /* Passed files         */
  25        struct ucred            creds;          /* Skb credentials      */
  26#ifdef CONFIG_SECURITY_NETWORK
  27        u32                     secid;          /* Passed security ID   */
  28#endif
  29};
  30
  31extern void scm_detach_fds(struct msghdr *msg, struct scm_cookie *scm);
  32extern void scm_detach_fds_compat(struct msghdr *msg, struct scm_cookie *scm);
  33extern int __scm_send(struct socket *sock, struct msghdr *msg, struct scm_cookie *scm);
  34extern void __scm_destroy(struct scm_cookie *scm);
  35extern struct scm_fp_list * scm_fp_dup(struct scm_fp_list *fpl);
  36
  37#ifdef CONFIG_SECURITY_NETWORK
  38static __inline__ void unix_get_peersec_dgram(struct socket *sock, struct scm_cookie *scm)
  39{
  40        security_socket_getpeersec_dgram(sock, NULL, &scm->secid);
  41}
  42#else
  43static __inline__ void unix_get_peersec_dgram(struct socket *sock, struct scm_cookie *scm)
  44{ }
  45#endif /* CONFIG_SECURITY_NETWORK */
  46
  47static __inline__ void scm_set_cred(struct scm_cookie *scm,
  48                                    struct pid *pid, const struct cred *cred)
  49{
  50        scm->pid  = get_pid(pid);
  51        scm->cred = cred ? get_cred(cred) : NULL;
  52        cred_to_ucred(pid, cred, &scm->creds);
  53}
  54
  55static __inline__ void scm_destroy_cred(struct scm_cookie *scm)
  56{
  57        put_pid(scm->pid);
  58        scm->pid  = NULL;
  59
  60        if (scm->cred)
  61                put_cred(scm->cred);
  62        scm->cred = NULL;
  63}
  64
  65static __inline__ void scm_destroy(struct scm_cookie *scm)
  66{
  67        scm_destroy_cred(scm);
  68        if (scm && scm->fp)
  69                __scm_destroy(scm);
  70}
  71
  72static __inline__ int scm_send(struct socket *sock, struct msghdr *msg,
  73                               struct scm_cookie *scm, bool forcecreds)
  74{
  75        memset(scm, 0, sizeof(*scm));
  76        if (forcecreds)
  77                scm_set_cred(scm, task_tgid(current), current_cred());
  78        unix_get_peersec_dgram(sock, scm);
  79        if (msg->msg_controllen <= 0)
  80                return 0;
  81        return __scm_send(sock, msg, scm);
  82}
  83
  84#ifdef CONFIG_SECURITY_NETWORK
  85static inline void scm_passec(struct socket *sock, struct msghdr *msg, struct scm_cookie *scm)
  86{
  87        char *secdata;
  88        u32 seclen;
  89        int err;
  90
  91        if (test_bit(SOCK_PASSSEC, &sock->flags)) {
  92                err = security_secid_to_secctx(scm->secid, &secdata, &seclen);
  93
  94                if (!err) {
  95                        put_cmsg(msg, SOL_SOCKET, SCM_SECURITY, seclen, secdata);
  96                        security_release_secctx(secdata, seclen);
  97                }
  98        }
  99}
 100#else
 101static inline void scm_passec(struct socket *sock, struct msghdr *msg, struct scm_cookie *scm)
 102{ }
 103#endif /* CONFIG_SECURITY_NETWORK */
 104
 105static __inline__ void scm_recv(struct socket *sock, struct msghdr *msg,
 106                                struct scm_cookie *scm, int flags)
 107{
 108        if (!msg->msg_control) {
 109                if (test_bit(SOCK_PASSCRED, &sock->flags) || scm->fp)
 110                        msg->msg_flags |= MSG_CTRUNC;
 111                scm_destroy(scm);
 112                return;
 113        }
 114
 115        if (test_bit(SOCK_PASSCRED, &sock->flags))
 116                put_cmsg(msg, SOL_SOCKET, SCM_CREDENTIALS, sizeof(scm->creds), &scm->creds);
 117
 118        scm_destroy_cred(scm);
 119
 120        scm_passec(sock, msg, scm);
 121
 122        if (!scm->fp)
 123                return;
 124        
 125        scm_detach_fds(msg, scm);
 126}
 127
 128
 129#endif /* __LINUX_NET_SCM_H */
 130
 131
lxr.linux.no kindly hosted by Redpill Linpro AS, provider of Linux consulting and operations services since 1995.