/* socket security operations */
 
-static u32 socket_sockcreate_sid(const struct task_security_struct *tsec)
+static int socket_sockcreate_sid(const struct task_security_struct *tsec,
+                                u16 secclass, u32 *socksid)
 {
-       return tsec->sockcreate_sid ? : tsec->sid;
+       if (tsec->sockcreate_sid > SECSID_NULL) {
+               *socksid = tsec->sockcreate_sid;
+               return 0;
+       }
+
+       return security_transition_sid(tsec->sid, tsec->sid, secclass, NULL,
+                                      socksid);
 }
 
 static int sock_has_perm(struct task_struct *task, struct sock *sk, u32 perms)
        const struct task_security_struct *tsec = current_security();
        u32 newsid;
        u16 secclass;
+       int rc;
 
        if (kern)
                return 0;
 
-       newsid = socket_sockcreate_sid(tsec);
        secclass = socket_type_to_security_class(family, type, protocol);
+       rc = socket_sockcreate_sid(tsec, secclass, &newsid);
+       if (rc)
+               return rc;
+
        return avc_has_perm(tsec->sid, newsid, secclass, SOCKET__CREATE, NULL);
 }
 
        struct sk_security_struct *sksec;
        int err = 0;
 
+       isec->sclass = socket_type_to_security_class(family, type, protocol);
+
        if (kern)
                isec->sid = SECINITSID_KERNEL;
-       else
-               isec->sid = socket_sockcreate_sid(tsec);
+       else {
+               err = socket_sockcreate_sid(tsec, isec->sclass, &(isec->sid));
+               if (err)
+                       return err;
+       }
 
-       isec->sclass = socket_type_to_security_class(family, type, protocol);
        isec->initialized = 1;
 
        if (sock->sk) {