Index: linux-2.4.31-rsbac-v1.2.4/include/rsbac/adf.h
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/include/rsbac/adf.h	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/include/rsbac/adf.h	(Arbeitskopie)
@@ -72,7 +72,10 @@
 extern int rsbac_sec_trunc(struct dentry * dentry_p,
                            loff_t new_len, loff_t old_len);
 
-extern void rsbac_symlink_redirect(struct dentry * dentry_p, char * name);
+char * rsbac_symlink_redirect(
+  struct dentry * dentry_p,
+  const char * name,
+  u_int maxlen);
 
 #ifdef CONFIG_RSBAC_ALLOW_DAC_DISABLE_PART
 extern int rsbac_dac_part_disabled(struct dentry * dentry_p);
Index: linux-2.4.31-rsbac-v1.2.4/include/rsbac/types.h
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/include/rsbac/types.h	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/include/rsbac/types.h	(Arbeitskopie)
@@ -4,7 +4,7 @@
 /*   Amon Ott <ao@rsbac.org>         */
 /* API: Data types for attributes    */
 /*      and standard module calls    */
-/* Last modified: 09/Feb/2005        */
+/* Last modified: 13/Apr/2005        */
 /*********************************** */
 
 #ifndef __RSBAC_TYPES_H
Index: linux-2.4.31-rsbac-v1.2.4/fs/ext2/symlink.c
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/fs/ext2/symlink.c	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/fs/ext2/symlink.c	(Arbeitskopie)
@@ -34,17 +34,16 @@
         int res;
 
 	/* copying is ugly, but we must not change the const */
-	rsbac_name = __getname();
-	if(!rsbac_name)
-	  return -ENOMEM;
-	strcpy(rsbac_name, s);
-        rsbac_symlink_redirect(dentry, rsbac_name);
-        res = vfs_readlink(dentry, buffer, buflen, rsbac_name);
-        putname(rsbac_name);
-        return res;
-#else
-	return vfs_readlink(dentry, buffer, buflen, s);
+        rsbac_name = rsbac_symlink_redirect(dentry, s, PAGE_SIZE);
+        if(rsbac_name)
+          {
+            res = vfs_readlink(dentry, buffer, buflen, rsbac_name);
+            kfree(rsbac_name);
+            return res;
+          }
+        else
 #endif
+	return vfs_readlink(dentry, buffer, buflen, s);
 }
 
 static int ext2_follow_link(struct dentry *dentry, struct nameidata *nd)
@@ -55,17 +54,16 @@
         int res;
 
 	/* copying is ugly, but we must not change the const */
-	rsbac_name = __getname();
-	if(!rsbac_name)
-	  return -ENOMEM;
-	strcpy(rsbac_name, s);
-        rsbac_symlink_redirect(dentry, rsbac_name);
-        res = vfs_follow_link(nd, rsbac_name);
-        putname(rsbac_name);
-        return res;
-#else
-	return vfs_follow_link(nd, s);
+        rsbac_name = rsbac_symlink_redirect(dentry, s, PAGE_SIZE);
+        if(rsbac_name)
+          {
+            res = vfs_follow_link(nd, rsbac_name);
+            kfree(rsbac_name);
+            return res;
+          }
+        else
 #endif
+	return vfs_follow_link(nd, s);
 }
 
 struct inode_operations ext2_fast_symlink_inode_operations = {
Index: linux-2.4.31-rsbac-v1.2.4/fs/ext3/symlink.c
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/fs/ext3/symlink.c	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/fs/ext3/symlink.c	(Arbeitskopie)
@@ -35,17 +35,16 @@
         int res;
 
 	/* copying is ugly, but we must not change the const */
-	rsbac_name = __getname();
-	if(!rsbac_name)
-	  return -ENOMEM;
-	strcpy(rsbac_name, s);
-        rsbac_symlink_redirect(dentry, rsbac_name);
-        res = vfs_readlink(dentry, buffer, buflen, rsbac_name);
-        putname(rsbac_name);
-        return res;
-#else
-	return vfs_readlink(dentry, buffer, buflen, s);
+        rsbac_name = rsbac_symlink_redirect(dentry, s, PAGE_SIZE);
+        if(rsbac_name)
+          {
+            res = vfs_readlink(dentry, buffer, buflen, rsbac_name);
+            kfree(rsbac_name);
+            return res;
+          }
+        else
 #endif
+	return vfs_readlink(dentry, buffer, buflen, s);
 }
 
 static int ext3_follow_link(struct dentry *dentry, struct nameidata *nd)
@@ -56,17 +55,16 @@
         int res;
 
 	/* copying is ugly, but we must not change the const */
-	rsbac_name = __getname();
-	if(!rsbac_name)
-	  return -ENOMEM;
-	strcpy(rsbac_name, s);
-        rsbac_symlink_redirect(dentry, rsbac_name);
-        res = vfs_follow_link(nd, rsbac_name);
-        putname(rsbac_name);
-        return res;
-#else
-	return vfs_follow_link(nd, s);
+        rsbac_name = rsbac_symlink_redirect(dentry, s, PAGE_SIZE);
+        if(rsbac_name)
+          {
+            res = vfs_follow_link(nd, rsbac_name);
+            kfree(rsbac_name);
+            return res;
+          }
+        else
 #endif
+	return vfs_follow_link(nd, s);
 }
 
 struct inode_operations ext3_fast_symlink_inode_operations = {
Index: linux-2.4.31-rsbac-v1.2.4/fs/namei.c
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/fs/namei.c	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/fs/namei.c	(Arbeitskopie)
@@ -2864,11 +2864,19 @@
 	struct page *page = NULL;
 	char *s = page_getlink(dentry, &page);
 	int res;
+#ifdef CONFIG_RSBAC_SYM_REDIR
+	char * rsbac_name;
+#endif
 
 #ifdef CONFIG_RSBAC_SYM_REDIR
-        rsbac_symlink_redirect(dentry, s);
+        rsbac_name = rsbac_symlink_redirect(dentry, s, PAGE_SIZE);
+        if(rsbac_name)
+          {
+            res = vfs_readlink(dentry,buffer,buflen,rsbac_name);
+            kfree(rsbac_name);
+          }
+        else
 #endif
-
 	res = vfs_readlink(dentry,buffer,buflen,s);
 	if (page) {
 		kunmap(page);
@@ -2882,11 +2890,19 @@
 	struct page *page = NULL;
 	char *s = page_getlink(dentry, &page);
 	int res;
+#ifdef CONFIG_RSBAC_SYM_REDIR
+	char * rsbac_name;
+#endif
 
 #ifdef CONFIG_RSBAC_SYM_REDIR
-        rsbac_symlink_redirect(dentry, s);
+        rsbac_name = rsbac_symlink_redirect(dentry, s, PAGE_SIZE);
+        if(rsbac_name)
+          {
+            res = __vfs_follow_link(nd, rsbac_name);
+            kfree(rsbac_name);
+          }
+        else
 #endif
-
 	res = __vfs_follow_link(nd, s);
 
 	if (page) {
Index: linux-2.4.31-rsbac-v1.2.4/rsbac/adf/adf_main.c
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/rsbac/adf/adf_main.c	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/rsbac/adf/adf_main.c	(Arbeitskopie)
@@ -2286,7 +2286,7 @@
 #endif
 
     return(error);
-  }; /* end of rsbac_adf_set_attr() */
+  } /* end of rsbac_adf_set_attr() */
 
 
 /****************
@@ -2715,57 +2715,49 @@
 #ifdef CONFIG_RSBAC_SYM_REDIR
 EXPORT_SYMBOL(rsbac_symlink_redirect);
 
-void rsbac_symlink_redirect(struct dentry * dentry_p, char * name)
+/* This function changes the symlink content by adding a suffix, if
+ * requested. It returns NULL, if unchanged, or a pointer to a
+ * kmalloc'd new char * otherwise, which has to be kfree'd after use.
+ */
+char * rsbac_symlink_redirect(
+  struct dentry * dentry_p,
+  const char * name,
+  u_int maxlen)
   {
     int                            err;
     union rsbac_target_id_t        i_tid;
+    char                         * new_name = NULL;
 #if defined(CONFIG_RSBAC_SYM_REDIR_MAC) || defined(CONFIG_RSBAC_SYM_REDIR_RC)
     union rsbac_target_id_t        i_tid2;
 #endif
     union rsbac_attribute_value_t  i_attr_val;
 
-    if(!name || !dentry_p || !dentry_p->d_inode)
-      return;
+    if(!name)
+      return NULL;
+    if(!dentry_p || !dentry_p->d_inode)
+      return NULL;
     if (!rsbac_is_initialized())
-      return;
+      return NULL;
 
-    i_tid.symlink.device = dentry_p->d_inode->i_sb->s_dev;
-    i_tid.symlink.inode = dentry_p->d_inode->i_ino;
-    i_tid.symlink.dentry_p = dentry_p;
     if(!S_ISLNK(dentry_p->d_inode->i_mode))
       {
-#ifdef CONFIG_RSBAC_RMSG
         rsbac_printk(KERN_DEBUG
                "rsbac_symlink_redirect(): called for non-symlink inode %u on dev %02u:%02u!\n",
                i_tid.symlink.inode,
                RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
-#endif
-#ifdef CONFIG_RSBAC_RMSG_NOSYSLOG
-        if (!rsbac_nosyslog)
-#endif
-        printk(KERN_DEBUG
-               "rsbac_symlink_redirect(): called for non-symlink inode %u on dev %02u:%02u!\n",
-               i_tid.symlink.inode,
-               RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
-        return;
+        return NULL;
       }
 
+    i_tid.symlink.device = dentry_p->d_inode->i_sb->s_dev;
+    i_tid.symlink.inode = dentry_p->d_inode->i_ino;
+    i_tid.symlink.dentry_p = dentry_p;
 #ifdef CONFIG_RSBAC_DEBUG
     if (rsbac_debug_aef)
       {
-#ifdef CONFIG_RSBAC_RMSG
         rsbac_printk(KERN_DEBUG
                "rsbac_symlink_redirect(): called for symlink inode %u on dev %02u:%02u!\n",
                i_tid.symlink.inode,
                RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
-#endif
-#ifdef CONFIG_RSBAC_RMSG_NOSYSLOG
-        if (!rsbac_nosyslog)
-#endif
-        printk(KERN_DEBUG
-               "rsbac_symlink_redirect(): called for symlink inode %u on dev %02u:%02u!\n",
-               i_tid.symlink.inode,
-               RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
       }
 #endif
 
@@ -2778,7 +2770,13 @@
                               FALSE) ))
       {
         rsbac_ds_get_error("rsbac_symlink_redirect()", A_symlink_add_uid);
-        return;  /* something weird happened */
+        if(new_name)
+          kfree(new_name);
+            rsbac_printk(KERN_DEBUG
+               "rsbac_symlink_redirect(): not enough space for symlink inode %u on dev %02u:%02u!\n",
+               i_tid.symlink.inode,
+               RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
+        return NULL;  /* something weird happened */
       }
     if(i_attr_val.symlink_add_uid)
       {
@@ -2791,10 +2789,33 @@
               && (name[len-1] <= '9')
              )
           len--;
-        if(len > (PAGE_SIZE - 20))
-          return;
+        if(len > (maxlen - 20))
+          {
+            if(new_name)
+              kfree(new_name);
+            rsbac_printk(KERN_DEBUG
+               "rsbac_symlink_redirect(): not enough space for symlink inode %u on dev %02u:%02u!\n",
+               i_tid.symlink.inode,
+               RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
+            return NULL;
+          }
         if(!rsbac_get_owner(&user))
-          ulongtostr(name+len, user);
+          {
+            if(!new_name)
+              {
+                new_name = kmalloc(maxlen, GFP_KERNEL);
+                if(!new_name)
+                  {
+                    rsbac_printk(KERN_DEBUG
+                                 "rsbac_symlink_redirect(): could not allocate memory for redirection of inode %u on dev %02u:%02u!\n",
+                                 i_tid.symlink.inode,
+                                 RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
+                    return NULL;
+                  }
+                strcpy(new_name, name);
+              }
+            ulongtostr(new_name+len, user);
+          }
       }
 #endif
 
@@ -2807,7 +2828,9 @@
                               FALSE) ))
       {
         rsbac_ds_get_error("rsbac_symlink_redirect()", A_symlink_add_mac_level);
-        return;  /* something weird happened */
+        if(new_name)
+          kfree(new_name);
+        return NULL;  /* something weird happened */
       }
     if(i_attr_val.symlink_add_mac_level)
       {
@@ -2825,11 +2848,19 @@
              )
           len--;
 #ifdef CONFIG_RSBAC_SYM_REDIR_MAC_CAT
-        if(len > (PAGE_SIZE - 85))
+        if(len > (maxlen - 85))
 #else
-        if(len > (PAGE_SIZE - 20))
+        if(len > (maxlen - 20))
 #endif
-          return;
+          {
+            if(new_name)
+              kfree(new_name);
+            rsbac_printk(KERN_DEBUG
+               "rsbac_symlink_redirect(): not enough space for symlink inode %u on dev %02u:%02u!\n",
+               i_tid.symlink.inode,
+               RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
+            return NULL;
+          }
 
         i_tid2.process = current->pid;
         if ((err = rsbac_get_attr(MAC,
@@ -2840,13 +2871,28 @@
                                   FALSE) ))
           {
             rsbac_ds_get_error("rsbac_symlink_redirect()", A_current_sec_level);
-            return;  /* something weird happened */
+            if(new_name)
+              kfree(new_name);
+            return NULL;  /* something weird happened */
           }
 
+        if(!new_name)
+          {
+            new_name = kmalloc(maxlen, GFP_KERNEL);
+            if(!new_name)
+              {
+                rsbac_printk(KERN_DEBUG
+                             "rsbac_symlink_redirect(): could not allocate memory for redirection of inode %u on dev %02u:%02u!\n",
+                             i_tid.symlink.inode,
+                             RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
+                return NULL;
+              }
+            strcpy(new_name, name);
+          }
 #ifdef CONFIG_RSBAC_SYM_REDIR_MAC_CAT
-        len+=sprintf(name+len, "%u:", i_attr_val.current_sec_level);
+        len+=sprintf(new_name+len, "%u:", i_attr_val.current_sec_level);
 #else
-        len+=sprintf(name+len, "%u", i_attr_val.current_sec_level);
+        len+=sprintf(new_name+len, "%u", i_attr_val.current_sec_level);
 #endif
 
 #ifdef CONFIG_RSBAC_SYM_REDIR_MAC_CAT
@@ -2858,9 +2904,11 @@
                                   FALSE) ))
           {
             rsbac_ds_get_error("rsbac_symlink_redirect()", A_mac_curr_categories);
-            return;  /* something weird happened */
+            if(new_name)
+              kfree(new_name);
+            return NULL;  /* something weird happened */
           }
-        u64tostrmac(name+len, i_attr_val.mac_categories);
+        u64tostrmac(new_name+len, i_attr_val.mac_categories);
 #endif
       }
 #endif
@@ -2874,7 +2922,9 @@
                               FALSE) ))
       {
         rsbac_ds_get_error("rsbac_symlink_redirect()", A_symlink_add_rc_role);
-        return;  /* something weird happened */
+        if(new_name)
+          kfree(new_name);
+        return NULL;  /* something weird happened */
       }
     if(i_attr_val.symlink_add_rc_role)
       {
@@ -2886,8 +2936,16 @@
               && (name[len-1] <= '9')
              )
           len--;
-        if(len > (PAGE_SIZE - 20))
-          return;
+        if(len > (maxlen - 20))
+          {
+            if(new_name)
+              kfree(new_name);
+            rsbac_printk(KERN_DEBUG
+               "rsbac_symlink_redirect(): not enough space for symlink inode %u on dev %02u:%02u!\n",
+               i_tid.symlink.inode,
+               RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
+            return NULL;
+          }
 
         i_tid2.process = current->pid;
         if ((err = rsbac_get_attr(RC,
@@ -2898,14 +2956,29 @@
                                   FALSE) ))
           {
             rsbac_ds_get_error("rsbac_symlink_redirect()", A_rc_role);
-            return;  /* something weird happened */
+            if(new_name)
+              kfree(new_name);
+            return NULL;  /* something weird happened */
           }
 
-        ulongtostr(name+len, i_attr_val.rc_role);
+        if(!new_name)
+          {
+            new_name = kmalloc(maxlen, GFP_KERNEL);
+            if(!new_name)
+              {
+                rsbac_printk(KERN_DEBUG
+                             "rsbac_symlink_redirect(): could not allocate memory for redirection of inode %u on dev %02u:%02u!\n",
+                             i_tid.symlink.inode,
+                             RSBAC_MAJOR(i_tid.symlink.device), RSBAC_MINOR(i_tid.symlink.device) );
+                return NULL;
+              }
+            strcpy(new_name, name);
+          }
+        ulongtostr(new_name+len, i_attr_val.rc_role);
       }
 #endif
 
-    return;
+    return new_name;
   }
 #endif
 
Index: linux-2.4.31-rsbac-v1.2.4/rsbac/adf/adf_check.c
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/rsbac/adf/adf_check.c	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/rsbac/adf/adf_check.c	(Arbeitskopie)
@@ -83,7 +83,7 @@
                 default: return(UNDEFINED);
               }
 
-#ifdef CONFIG_RSBAC_DAC_OWNER
+#ifdef CONFIG_RSBAC_DAC_GROUP
         case R_CHANGE_DAC_EFF_GROUP:
         case R_CHANGE_DAC_FS_GROUP:
             switch(target)
Index: linux-2.4.31-rsbac-v1.2.4/rsbac/data_structures/aci_data_structures.c
===================================================================
--- linux-2.4.31-rsbac-v1.2.4/rsbac/data_structures/aci_data_structures.c	(Revision 343)
+++ linux-2.4.31-rsbac-v1.2.4/rsbac/data_structures/aci_data_structures.c	(Arbeitskopie)
@@ -14305,7 +14305,18 @@
                   read_lock(&tasklist_lock);
                   task_p = find_task_by_pid(tid_p->process);
                   if(task_p)
-                    value->pax_flags = task_p->flags & RSBAC_PAX_ALL_FLAGS;
+                    {
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,10)
+  #if defined(CONFIG_PAX_NOEXEC) || defined(CONFIG_PAX_ASLR)
+                      if(task_p->mm)
+                        value->pax_flags = task_p->mm->flags & RSBAC_PAX_ALL_FLAGS;
+                      else
+  #endif
+                        value->pax_flags = 0;
+#else
+                      value->pax_flags = task_p->flags & RSBAC_PAX_ALL_FLAGS;
+#endif
+                    }
                   else
                     err = -RSBAC_EINVALIDTARGET;
                   read_unlock(&tasklist_lock);
@@ -15625,7 +15636,7 @@
                                          device_p->handles.pax[pax_fd_hash(tid_p->file.inode)],
                                          0,
                                          &tid_p->file.inode,
-                                         &value_p->data_type);
+                                         &value_p->pax_flags);
                     break;
 
                   default:
