aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--main/linux-grsec/APKBUILD12
-rw-r--r--main/linux-grsec/grsecurity-2.2.2-3.2.2-201201252117.patch (renamed from main/linux-grsec/grsecurity-2.2.2-3.2.1-201201221501.patch)828
-rw-r--r--main/linux-grsec/kernelconfig.x863
-rw-r--r--main/linux-grsec/kernelconfig.x86_641
4 files changed, 236 insertions, 608 deletions
diff --git a/main/linux-grsec/APKBUILD b/main/linux-grsec/APKBUILD
index 8ef503f326..c846f07ee1 100644
--- a/main/linux-grsec/APKBUILD
+++ b/main/linux-grsec/APKBUILD
@@ -2,7 +2,7 @@
_flavor=grsec
pkgname=linux-${_flavor}
-pkgver=3.2.1
+pkgver=3.2.2
_kernver=3.2
pkgrel=0
pkgdesc="Linux kernel with grsecurity"
@@ -14,7 +14,7 @@ _config=${config:-kernelconfig.${CARCH}}
install=
source="ftp://ftp.kernel.org/pub/linux/kernel/v3.0/linux-$_kernver.tar.bz2
ftp://ftp.kernel.org/pub/linux/kernel/v3.0/patch-$pkgver.bz2
- grsecurity-2.2.2-3.2.1-201201221501.patch
+ grsecurity-2.2.2-3.2.2-201201252117.patch
0004-arp-flush-arp-cache-on-device-change.patch
@@ -140,10 +140,10 @@ dev() {
}
md5sums="7ceb61f87c097fc17509844b71268935 linux-3.2.tar.bz2
-31fc34340f11118873463a1d59d47b7f patch-3.2.1.bz2
-2248338d08df062a843a0b601064e781 grsecurity-2.2.2-3.2.1-201201221501.patch
+e9e53fba37c5e2afa4cdecab234120bd patch-3.2.2.bz2
+c50a77c1b3a7317fad080e64569ad8dd grsecurity-2.2.2-3.2.2-201201252117.patch
776adeeb5272093574f8836c5037dd7d 0004-arp-flush-arp-cache-on-device-change.patch
f3eda7112ef074a4121ec6de943c63ee x86-centaur-enable-cx8-for-via-eden-too.patch
62cc7d7b5ba7ef05b72ff91c0411c189 linux-3.0.x-regression-with-ipv4-routes-having-mtu.patch
-c21699aa138e209cd889582c2ef80e61 kernelconfig.x86
-af26ec54258f5cde5fa41c434abae34e kernelconfig.x86_64"
+fca35f0f47e31720a87ba9d3bedf76aa kernelconfig.x86
+79ae970fb58cc5eac8fcf0af0cc6f710 kernelconfig.x86_64"
diff --git a/main/linux-grsec/grsecurity-2.2.2-3.2.1-201201221501.patch b/main/linux-grsec/grsecurity-2.2.2-3.2.2-201201252117.patch
index ff965370cf..4d4d52eccf 100644
--- a/main/linux-grsec/grsecurity-2.2.2-3.2.1-201201221501.patch
+++ b/main/linux-grsec/grsecurity-2.2.2-3.2.2-201201252117.patch
@@ -186,7 +186,7 @@ index 81c287f..d456d02 100644
pcd. [PARIDE]
diff --git a/Makefile b/Makefile
-index c5edffa..26654d7 100644
+index 2f684da..bf21f8d 100644
--- a/Makefile
+++ b/Makefile
@@ -245,8 +245,9 @@ CONFIG_SHELL := $(shell if [ -x "$$BASH" ]; then echo $$BASH; \
@@ -22993,7 +22993,7 @@ index d87dd6d..bf3fa66 100644
pte = kmemcheck_pte_lookup(address);
diff --git a/arch/x86/mm/mmap.c b/arch/x86/mm/mmap.c
-index 4b5ba85..f166ad2 100644
+index 845df68..1d8d29f 100644
--- a/arch/x86/mm/mmap.c
+++ b/arch/x86/mm/mmap.c
@@ -52,7 +52,7 @@ static unsigned int stack_maxrandom_size(void)
@@ -24900,18 +24900,10 @@ index 7b72502..646105c 100644
err = -EFAULT;
goto out;
diff --git a/block/scsi_ioctl.c b/block/scsi_ioctl.c
-index fbdf0d8..e8f3caf 100644
+index 688be8a..8a37d98 100644
--- a/block/scsi_ioctl.c
+++ b/block/scsi_ioctl.c
-@@ -24,6 +24,7 @@
- #include <linux/capability.h>
- #include <linux/completion.h>
- #include <linux/cdrom.h>
-+#include <linux/ratelimit.h>
- #include <linux/slab.h>
- #include <linux/times.h>
- #include <asm/uaccess.h>
-@@ -222,8 +223,20 @@ EXPORT_SYMBOL(blk_verify_command);
+@@ -223,8 +223,20 @@ EXPORT_SYMBOL(blk_verify_command);
static int blk_fill_sghdr_rq(struct request_queue *q, struct request *rq,
struct sg_io_hdr *hdr, fmode_t mode)
{
@@ -24933,7 +24925,7 @@ index fbdf0d8..e8f3caf 100644
if (blk_verify_command(rq->cmd, mode & FMODE_WRITE))
return -EPERM;
-@@ -432,6 +445,8 @@ int sg_scsi_ioctl(struct request_queue *q, struct gendisk *disk, fmode_t mode,
+@@ -433,6 +445,8 @@ int sg_scsi_ioctl(struct request_queue *q, struct gendisk *disk, fmode_t mode,
int err;
unsigned int in_len, out_len, bytes, opcode, cmdlen;
char *buffer = NULL, sense[SCSI_SENSE_BUFFERSIZE];
@@ -24942,7 +24934,7 @@ index fbdf0d8..e8f3caf 100644
if (!sic)
return -EINVAL;
-@@ -465,9 +480,18 @@ int sg_scsi_ioctl(struct request_queue *q, struct gendisk *disk, fmode_t mode,
+@@ -466,9 +480,18 @@ int sg_scsi_ioctl(struct request_queue *q, struct gendisk *disk, fmode_t mode,
*/
err = -EFAULT;
rq->cmd_len = cmdlen;
@@ -24962,64 +24954,6 @@ index fbdf0d8..e8f3caf 100644
if (in_len && copy_from_user(buffer, sic->data + cmdlen, in_len))
goto error;
-@@ -690,6 +714,57 @@ int scsi_cmd_ioctl(struct request_queue *q, struct gendisk *bd_disk, fmode_t mod
- }
- EXPORT_SYMBOL(scsi_cmd_ioctl);
-
-+int scsi_verify_blk_ioctl(struct block_device *bd, unsigned int cmd)
-+{
-+ if (bd && bd == bd->bd_contains)
-+ return 0;
-+
-+ /* Actually none of these is particularly useful on a partition,
-+ * but they are safe.
-+ */
-+ switch (cmd) {
-+ case SCSI_IOCTL_GET_IDLUN:
-+ case SCSI_IOCTL_GET_BUS_NUMBER:
-+ case SCSI_IOCTL_GET_PCI:
-+ case SCSI_IOCTL_PROBE_HOST:
-+ case SG_GET_VERSION_NUM:
-+ case SG_SET_TIMEOUT:
-+ case SG_GET_TIMEOUT:
-+ case SG_GET_RESERVED_SIZE:
-+ case SG_SET_RESERVED_SIZE:
-+ case SG_EMULATED_HOST:
-+ return 0;
-+ case CDROM_GET_CAPABILITY:
-+ /* Keep this until we remove the printk below. udev sends it
-+ * and we do not want to spam dmesg about it. CD-ROMs do
-+ * not have partitions, so we get here only for disks.
-+ */
-+ return -ENOIOCTLCMD;
-+ default:
-+ break;
-+ }
-+
-+ /* In particular, rule out all resets and host-specific ioctls. */
-+ printk_ratelimited(KERN_WARNING
-+ "%s: sending ioctl %x to a partition!\n", current->comm, cmd);
-+
-+ return capable(CAP_SYS_RAWIO) ? 0 : -ENOIOCTLCMD;
-+}
-+EXPORT_SYMBOL(scsi_verify_blk_ioctl);
-+
-+int scsi_cmd_blk_ioctl(struct block_device *bd, fmode_t mode,
-+ unsigned int cmd, void __user *arg)
-+{
-+ int ret;
-+
-+ ret = scsi_verify_blk_ioctl(bd, cmd);
-+ if (ret < 0)
-+ return ret;
-+
-+ return scsi_cmd_ioctl(bd->bd_disk->queue, bd->bd_disk, mode, cmd, arg);
-+}
-+EXPORT_SYMBOL(scsi_cmd_blk_ioctl);
-+
- static int __init blk_scsi_ioctl_init(void)
- {
- blk_set_cmd_filter_defaults(&blk_default_cmd_filter);
diff --git a/crypto/cryptd.c b/crypto/cryptd.c
index 671d4d6..5f24030 100644
--- a/crypto/cryptd.c
@@ -26281,7 +26215,7 @@ index caf995f..6f76697 100644
/**
diff --git a/drivers/block/cciss.c b/drivers/block/cciss.c
-index 587cce5..77b928b 100644
+index b0f553b..77b928b 100644
--- a/drivers/block/cciss.c
+++ b/drivers/block/cciss.c
@@ -1198,6 +1198,8 @@ static int cciss_ioctl32_passthru(struct block_device *bdev, fmode_t mode,
@@ -26293,27 +26227,6 @@ index 587cce5..77b928b 100644
err = 0;
err |=
copy_from_user(&arg64.LUN_info, &arg32->LUN_info,
-@@ -1735,7 +1737,7 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode,
- case CCISS_BIG_PASSTHRU:
- return cciss_bigpassthru(h, argp);
-
-- /* scsi_cmd_ioctl handles these, below, though some are not */
-+ /* scsi_cmd_blk_ioctl handles these, below, though some are not */
- /* very meaningful for cciss. SG_IO is the main one people want. */
-
- case SG_GET_VERSION_NUM:
-@@ -1746,9 +1748,9 @@ static int cciss_ioctl(struct block_device *bdev, fmode_t mode,
- case SG_EMULATED_HOST:
- case SG_IO:
- case SCSI_IOCTL_SEND_COMMAND:
-- return scsi_cmd_ioctl(disk->queue, disk, mode, cmd, argp);
-+ return scsi_cmd_blk_ioctl(bdev, mode, cmd, argp);
-
-- /* scsi_cmd_ioctl would normally handle these, below, but */
-+ /* scsi_cmd_blk_ioctl would normally handle these, below, but */
- /* they aren't a good fit for cciss, as CD-ROMs are */
- /* not supported, and we don't have any bus/target/lun */
- /* which we present to the kernel. */
@@ -3007,7 +3009,7 @@ static void start_io(ctlr_info_t *h)
while (!list_empty(&h->reqQ)) {
c = list_entry(h->reqQ.next, CommandList_struct, list);
@@ -26828,57 +26741,6 @@ index 1e888c9..05cf1b0 100644
set_fs(old_fs);
if (likely(bw == len))
return 0;
-diff --git a/drivers/block/ub.c b/drivers/block/ub.c
-index 0e376d4..7333b9e 100644
---- a/drivers/block/ub.c
-+++ b/drivers/block/ub.c
-@@ -1744,12 +1744,11 @@ static int ub_bd_release(struct gendisk *disk, fmode_t mode)
- static int ub_bd_ioctl(struct block_device *bdev, fmode_t mode,
- unsigned int cmd, unsigned long arg)
- {
-- struct gendisk *disk = bdev->bd_disk;
- void __user *usermem = (void __user *) arg;
- int ret;
-
- mutex_lock(&ub_mutex);
-- ret = scsi_cmd_ioctl(disk->queue, disk, mode, cmd, usermem);
-+ ret = scsi_cmd_blk_ioctl(bdev, mode, cmd, usermem);
- mutex_unlock(&ub_mutex);
-
- return ret;
-diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c
-index 4d0b70a..e46f2f7 100644
---- a/drivers/block/virtio_blk.c
-+++ b/drivers/block/virtio_blk.c
-@@ -243,8 +243,8 @@ static int virtblk_ioctl(struct block_device *bdev, fmode_t mode,
- if (!virtio_has_feature(vblk->vdev, VIRTIO_BLK_F_SCSI))
- return -ENOTTY;
-
-- return scsi_cmd_ioctl(disk->queue, disk, mode, cmd,
-- (void __user *)data);
-+ return scsi_cmd_blk_ioctl(bdev, mode, cmd,
-+ (void __user *)data);
- }
-
- /* We provide getgeo only to please some old bootloader/partitioning tools */
-diff --git a/drivers/cdrom/cdrom.c b/drivers/cdrom/cdrom.c
-index f997c27..cedb231 100644
---- a/drivers/cdrom/cdrom.c
-+++ b/drivers/cdrom/cdrom.c
-@@ -2747,12 +2747,11 @@ int cdrom_ioctl(struct cdrom_device_info *cdi, struct block_device *bdev,
- {
- void __user *argp = (void __user *)arg;
- int ret;
-- struct gendisk *disk = bdev->bd_disk;
-
- /*
- * Try the generic SCSI command ioctl's first.
- */
-- ret = scsi_cmd_ioctl(disk->queue, disk, mode, cmd, argp);
-+ ret = scsi_cmd_blk_ioctl(bdev, mode, cmd, argp);
- if (ret != -ENOTTY)
- return ret;
-
diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig
index 4364303..9adf4ee 100644
--- a/drivers/char/Kconfig
@@ -27713,6 +27575,19 @@ index b153674..ad2ba9b 100644
{
PCI_DEVICE(PCI_VENDOR_ID_RADISYS, R82600_BRIDGE_ID)
},
+diff --git a/drivers/edac/sb_edac.c b/drivers/edac/sb_edac.c
+index 7a402bf..af0b211 100644
+--- a/drivers/edac/sb_edac.c
++++ b/drivers/edac/sb_edac.c
+@@ -367,7 +367,7 @@ static const struct pci_id_table pci_dev_descr_sbridge_table[] = {
+ /*
+ * pci_device_id table for which devices we are looking for
+ */
+-static const struct pci_device_id sbridge_pci_tbl[] __devinitdata = {
++static const struct pci_device_id sbridge_pci_tbl[] __devinitconst = {
+ {PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_SBRIDGE_IMC_TA)},
+ {0,} /* 0 terminated list. */
+ };
diff --git a/drivers/edac/x38_edac.c b/drivers/edac/x38_edac.c
index b6f47de..c5acf3a 100644
--- a/drivers/edac/x38_edac.c
@@ -28721,10 +28596,10 @@ index 8227e76..ce0b195 100644
/*
* Asic structures
diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
-index c4d00a1..f0fdc90 100644
+index 9b39145..389b93b 100644
--- a/drivers/gpu/drm/radeon/radeon_device.c
+++ b/drivers/gpu/drm/radeon/radeon_device.c
-@@ -684,7 +684,7 @@ static bool radeon_switcheroo_can_switch(struct pci_dev *pdev)
+@@ -687,7 +687,7 @@ static bool radeon_switcheroo_can_switch(struct pci_dev *pdev)
bool can_switch;
spin_lock(&dev->count_lock);
@@ -29062,10 +28937,10 @@ index 8a8725c..afed796 100644
marker = list_first_entry(&queue->head,
struct vmw_marker, head);
diff --git a/drivers/hid/hid-core.c b/drivers/hid/hid-core.c
-index af35384..5ab3c36 100644
+index bb656d8..4169fca 100644
--- a/drivers/hid/hid-core.c
+++ b/drivers/hid/hid-core.c
-@@ -2000,7 +2000,7 @@ static bool hid_ignore(struct hid_device *hdev)
+@@ -2012,7 +2012,7 @@ static bool hid_ignore(struct hid_device *hdev)
int hid_add_device(struct hid_device *hdev)
{
@@ -29074,7 +28949,7 @@ index af35384..5ab3c36 100644
int ret;
if (WARN_ON(hdev->status & HID_STAT_ADDED))
-@@ -2015,7 +2015,7 @@ int hid_add_device(struct hid_device *hdev)
+@@ -2027,7 +2027,7 @@ int hid_add_device(struct hid_device *hdev)
/* XXX hack, any other cleaner solution after the driver core
* is converted to allow more than 20 bytes as the device name? */
dev_set_name(&hdev->dev, "%04X:%04X:%04X.%04X", hdev->bus,
@@ -29500,20 +29375,6 @@ index 8126824..55a2798 100644
drive->dma = 0;
}
}
-diff --git a/drivers/ide/ide-floppy_ioctl.c b/drivers/ide/ide-floppy_ioctl.c
-index d267b7a..a22ca84 100644
---- a/drivers/ide/ide-floppy_ioctl.c
-+++ b/drivers/ide/ide-floppy_ioctl.c
-@@ -292,8 +292,7 @@ int ide_floppy_ioctl(ide_drive_t *drive, struct block_device *bdev,
- * and CDROM_SEND_PACKET (legacy) ioctls
- */
- if (cmd != CDROM_SEND_PACKET && cmd != SCSI_IOCTL_SEND_COMMAND)
-- err = scsi_cmd_ioctl(bdev->bd_disk->queue, bdev->bd_disk,
-- mode, cmd, argp);
-+ err = scsi_cmd_blk_ioctl(bdev, mode, cmd, argp);
-
- if (err == -ENOTTY)
- err = generic_ide_ioctl(drive, bdev, cmd, arg);
diff --git a/drivers/ide/ide-pci-generic.c b/drivers/ide/ide-pci-generic.c
index a743e68..1cfd674 100644
--- a/drivers/ide/ide-pci-generic.c
@@ -31441,10 +31302,10 @@ index 1cbfc6b..56e1dbb 100644
/*----------------------------------------------------------------*/
diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c
-index ede2461..9c4c691 100644
+index 7d9e071..015b1d5 100644
--- a/drivers/md/raid1.c
+++ b/drivers/md/raid1.c
-@@ -1559,7 +1559,7 @@ static int fix_sync_read_error(struct r1bio *r1_bio)
+@@ -1568,7 +1568,7 @@ static int fix_sync_read_error(struct r1bio *r1_bio)
if (r1_sync_page_io(rdev, sect, s,
bio->bi_io_vec[idx].bv_page,
READ) != 0)
@@ -31453,7 +31314,7 @@ index ede2461..9c4c691 100644
}
sectors -= s;
sect += s;
-@@ -1772,7 +1772,7 @@ static void fix_read_error(struct r1conf *conf, int read_disk,
+@@ -1781,7 +1781,7 @@ static void fix_read_error(struct r1conf *conf, int read_disk,
test_bit(In_sync, &rdev->flags)) {
if (r1_sync_page_io(rdev, sect, s,
conf->tmppage, READ)) {
@@ -33232,7 +33093,7 @@ index b592016..fe47870 100644
| set11nRateFlags(i->rates, 2)
| set11nRateFlags(i->rates, 3)
diff --git a/drivers/net/wireless/ath/ath9k/ar9003_mac.c b/drivers/net/wireless/ath/ath9k/ar9003_mac.c
-index ccde784..db012b3 100644
+index f5ae3c6..7936af3 100644
--- a/drivers/net/wireless/ath/ath9k/ar9003_mac.c
+++ b/drivers/net/wireless/ath/ath9k/ar9003_mac.c
@@ -35,47 +35,47 @@ ar9003_set_txdesc(struct ath_hw *ah, void *ds, struct ath_tx_info *i)
@@ -33398,10 +33259,10 @@ index bea8524..c677c06 100644
struct brcms_phy {
struct brcms_phy_pub pubpi_ro;
diff --git a/drivers/net/wireless/iwlegacy/iwl3945-base.c b/drivers/net/wireless/iwlegacy/iwl3945-base.c
-index b282d86..bee832f 100644
+index 05f2ad1..ae00eea 100644
--- a/drivers/net/wireless/iwlegacy/iwl3945-base.c
+++ b/drivers/net/wireless/iwlegacy/iwl3945-base.c
-@@ -3686,7 +3686,9 @@ static int iwl3945_pci_probe(struct pci_dev *pdev, const struct pci_device_id *e
+@@ -3685,7 +3685,9 @@ static int iwl3945_pci_probe(struct pci_dev *pdev, const struct pci_device_id *e
*/
if (iwl3945_mod_params.disable_hw_scan) {
IWL_DEBUG_INFO(priv, "Disabling hw_scan\n");
@@ -34938,51 +34799,6 @@ index 21a045e..ec89e03 100644
dev_set_name(&rport->dev, "port-%d:%d", shost->host_no, id);
transport_setup_device(&rport->dev);
-diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c
-index fa3a591..fd96409 100644
---- a/drivers/scsi/sd.c
-+++ b/drivers/scsi/sd.c
-@@ -1074,6 +1074,10 @@ static int sd_ioctl(struct block_device *bdev, fmode_t mode,
- SCSI_LOG_IOCTL(1, sd_printk(KERN_INFO, sdkp, "sd_ioctl: disk=%s, "
- "cmd=0x%x\n", disk->disk_name, cmd));
-
-+ error = scsi_verify_blk_ioctl(bdev, cmd);
-+ if (error < 0)
-+ return error;
-+
- /*
- * If we are in the middle of error recovery, don't let anyone
- * else try and use this device. Also, if error recovery fails, it
-@@ -1096,7 +1100,7 @@ static int sd_ioctl(struct block_device *bdev, fmode_t mode,
- error = scsi_ioctl(sdp, cmd, p);
- break;
- default:
-- error = scsi_cmd_ioctl(disk->queue, disk, mode, cmd, p);
-+ error = scsi_cmd_blk_ioctl(bdev, mode, cmd, p);
- if (error != -ENOTTY)
- break;
- error = scsi_ioctl(sdp, cmd, p);
-@@ -1266,6 +1270,11 @@ static int sd_compat_ioctl(struct block_device *bdev, fmode_t mode,
- unsigned int cmd, unsigned long arg)
- {
- struct scsi_device *sdev = scsi_disk(bdev->bd_disk)->device;
-+ int ret;
-+
-+ ret = scsi_verify_blk_ioctl(bdev, cmd);
-+ if (ret < 0)
-+ return ret;
-
- /*
- * If we are in the middle of error recovery, don't let anyone
-@@ -1277,8 +1286,6 @@ static int sd_compat_ioctl(struct block_device *bdev, fmode_t mode,
- return -ENODEV;
-
- if (sdev->host->hostt->compat_ioctl) {
-- int ret;
--
- ret = sdev->host->hostt->compat_ioctl(sdev, cmd, (void __user *)arg);
-
- return ret;
diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c
index 441a1c5..07cece7 100644
--- a/drivers/scsi/sg.c
@@ -35474,7 +35290,7 @@ index 6845228..df77141 100644
core_tmr_handle_tas_abort(tmr_nacl, cmd, tas, fe_count);
diff --git a/drivers/target/target_core_transport.c b/drivers/target/target_core_transport.c
-index 0257658..09433d5 100644
+index e87d0eb..856cbcc 100644
--- a/drivers/target/target_core_transport.c
+++ b/drivers/target/target_core_transport.c
@@ -1343,7 +1343,7 @@ struct se_device *transport_add_device_to_core_hba(
@@ -35525,7 +35341,7 @@ index 0257658..09433d5 100644
spin_unlock_irqrestore(&cmd->t_state_lock, flags);
return false;
}
-@@ -4495,7 +4495,7 @@ int transport_check_aborted_status(struct se_cmd *cmd, int send_status)
+@@ -4509,7 +4509,7 @@ int transport_check_aborted_status(struct se_cmd *cmd, int send_status)
{
int ret = 0;
@@ -35534,7 +35350,7 @@ index 0257658..09433d5 100644
if (!send_status ||
(cmd->se_cmd_flags & SCF_SENT_DELAYED_TAS))
return 1;
-@@ -4532,7 +4532,7 @@ void transport_send_task_abort(struct se_cmd *cmd)
+@@ -4546,7 +4546,7 @@ void transport_send_task_abort(struct se_cmd *cmd)
*/
if (cmd->data_direction == DMA_TO_DEVICE) {
if (cmd->se_tfo->write_pending_status(cmd) != 0) {
@@ -39567,7 +39383,7 @@ index 79e2ca7..5828ad1 100644
A.out (Assembler.OUTput) is a set of formats for libraries and
executables used in the earliest versions of UNIX. Linux used
diff --git a/fs/aio.c b/fs/aio.c
-index 78c514c..22ac304 100644
+index 969beb0..09fab51 100644
--- a/fs/aio.c
+++ b/fs/aio.c
@@ -119,7 +119,7 @@ static int aio_setup_ring(struct kioctx *ctx)
@@ -39579,7 +39395,7 @@ index 78c514c..22ac304 100644
return -EINVAL;
nr_events = (PAGE_SIZE * nr_pages - sizeof(struct aio_ring)) / sizeof(struct io_event);
-@@ -1454,22 +1454,27 @@ static ssize_t aio_fsync(struct kiocb *iocb)
+@@ -1461,22 +1461,27 @@ static ssize_t aio_fsync(struct kiocb *iocb)
static ssize_t aio_setup_vectored_rw(int type, struct kiocb *kiocb, bool compat)
{
ssize_t ret;
@@ -41454,10 +41270,10 @@ index 9a37a9b..35792b6 100644
/*
* We'll have a dentry and an inode for
diff --git a/fs/dcache.c b/fs/dcache.c
-index 89509b5..d33331b 100644
+index f7908ae..920a680 100644
--- a/fs/dcache.c
+++ b/fs/dcache.c
-@@ -3056,7 +3056,7 @@ void __init vfs_caches_init(unsigned long mempages)
+@@ -3042,7 +3042,7 @@ void __init vfs_caches_init(unsigned long mempages)
mempages -= reserve;
names_cachep = kmem_cache_create("names_cache", PATH_MAX, 0,
@@ -41533,7 +41349,7 @@ index 3745f7c..89cc7a3 100644
return rc;
}
diff --git a/fs/exec.c b/fs/exec.c
-index 3625464..8dcadcf 100644
+index 3625464..d08b205 100644
--- a/fs/exec.c
+++ b/fs/exec.c
@@ -55,12 +55,28 @@
@@ -41800,7 +41616,18 @@ index 3625464..8dcadcf 100644
/*
* We move the actual failure in case of RLIMIT_NPROC excess from
* set*uid() to execve() because too many poorly written programs
-@@ -1503,6 +1531,16 @@ static int do_execve_common(const char *filename,
+@@ -1497,12 +1525,27 @@ static int do_execve_common(const char *filename,
+ if (IS_ERR(file))
+ goto out_unmark;
+
++ if (gr_ptrace_readexec(file, bprm->unsafe)) {
++ retval = -EPERM;
++ goto out_file;
++ }
++
+ sched_exec();
+
+ bprm->file = file;
bprm->filename = filename;
bprm->interp = filename;
@@ -41817,7 +41644,7 @@ index 3625464..8dcadcf 100644
retval = bprm_mm_init(bprm);
if (retval)
goto out_file;
-@@ -1532,9 +1570,40 @@ static int do_execve_common(const char *filename,
+@@ -1532,9 +1575,40 @@ static int do_execve_common(const char *filename,
if (retval < 0)
goto out;
@@ -41859,7 +41686,7 @@ index 3625464..8dcadcf 100644
/* execve succeeded */
current->fs->in_exec = 0;
-@@ -1545,6 +1614,14 @@ static int do_execve_common(const char *filename,
+@@ -1545,6 +1619,14 @@ static int do_execve_common(const char *filename,
put_files_struct(displaced);
return retval;
@@ -41874,7 +41701,7 @@ index 3625464..8dcadcf 100644
out:
if (bprm->mm) {
acct_arg_size(bprm, 0);
-@@ -1618,7 +1695,7 @@ static int expand_corename(struct core_name *cn)
+@@ -1618,7 +1700,7 @@ static int expand_corename(struct core_name *cn)
{
char *old_corename = cn->corename;
@@ -41883,7 +41710,7 @@ index 3625464..8dcadcf 100644
cn->corename = krealloc(old_corename, cn->size, GFP_KERNEL);
if (!cn->corename) {
-@@ -1715,7 +1792,7 @@ static int format_corename(struct core_name *cn, long signr)
+@@ -1715,7 +1797,7 @@ static int format_corename(struct core_name *cn, long signr)
int pid_in_pattern = 0;
int err = 0;
@@ -41892,7 +41719,7 @@ index 3625464..8dcadcf 100644
cn->corename = kmalloc(cn->size, GFP_KERNEL);
cn->used = 0;
-@@ -1812,6 +1889,218 @@ out:
+@@ -1812,6 +1894,218 @@ out:
return ispipe;
}
@@ -42111,7 +41938,7 @@ index 3625464..8dcadcf 100644
static int zap_process(struct task_struct *start, int exit_code)
{
struct task_struct *t;
-@@ -2023,17 +2312,17 @@ static void wait_for_dump_helpers(struct file *file)
+@@ -2023,17 +2317,17 @@ static void wait_for_dump_helpers(struct file *file)
pipe = file->f_path.dentry->d_inode->i_pipe;
pipe_lock(pipe);
@@ -42134,7 +41961,7 @@ index 3625464..8dcadcf 100644
pipe_unlock(pipe);
}
-@@ -2094,7 +2383,7 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
+@@ -2094,7 +2388,7 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
int retval = 0;
int flag = 0;
int ispipe;
@@ -42143,7 +41970,7 @@ index 3625464..8dcadcf 100644
struct coredump_params cprm = {
.signr = signr,
.regs = regs,
-@@ -2109,6 +2398,9 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
+@@ -2109,6 +2403,9 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
audit_core_dumps(signr);
@@ -42153,7 +41980,7 @@ index 3625464..8dcadcf 100644
binfmt = mm->binfmt;
if (!binfmt || !binfmt->core_dump)
goto fail;
-@@ -2176,7 +2468,7 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
+@@ -2176,7 +2473,7 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
}
cprm.limit = RLIM_INFINITY;
@@ -42162,7 +41989,7 @@ index 3625464..8dcadcf 100644
if (core_pipe_limit && (core_pipe_limit < dump_count)) {
printk(KERN_WARNING "Pid %d(%s) over core_pipe_limit\n",
task_tgid_vnr(current), current->comm);
-@@ -2203,6 +2495,8 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
+@@ -2203,6 +2500,8 @@ void do_coredump(long signr, int exit_code, struct pt_regs *regs)
} else {
struct inode *inode;
@@ -42171,7 +41998,7 @@ index 3625464..8dcadcf 100644
if (cprm.limit < binfmt->min_coredump)
goto fail_unlock;
-@@ -2246,7 +2540,7 @@ close_fail:
+@@ -2246,7 +2545,7 @@ close_fail:
filp_close(cprm.file, NULL);
fail_dropcount:
if (ispipe)
@@ -42180,7 +42007,7 @@ index 3625464..8dcadcf 100644
fail_unlock:
kfree(cn.corename);
fail_corename:
-@@ -2265,7 +2559,7 @@ fail:
+@@ -2265,7 +2564,7 @@ fail:
*/
int dump_write(struct file *file, const void *addr, int nr)
{
@@ -44688,7 +44515,7 @@ index cfc6d44..b4632a5 100644
error = lock_mount(&old);
if (error)
diff --git a/fs/nfs/blocklayout/blocklayout.c b/fs/nfs/blocklayout/blocklayout.c
-index 281ae95..dd895b9 100644
+index 3db6b82..a57597e 100644
--- a/fs/nfs/blocklayout/blocklayout.c
+++ b/fs/nfs/blocklayout/blocklayout.c
@@ -90,7 +90,7 @@ static int is_writable(struct pnfs_block_extent *be, sector_t isect)
@@ -44778,32 +44605,6 @@ index 9fde1c0..14e8827 100644
fanotify_event_metadata.event_len))
goto out_kill_access_response;
-diff --git a/fs/notify/mark.c b/fs/notify/mark.c
-index e14587d..f104d56 100644
---- a/fs/notify/mark.c
-+++ b/fs/notify/mark.c
-@@ -135,9 +135,6 @@ void fsnotify_destroy_mark(struct fsnotify_mark *mark)
-
- mark->flags &= ~FSNOTIFY_MARK_FLAG_ALIVE;
-
-- /* 1 from caller and 1 for being on i_list/g_list */
-- BUG_ON(atomic_read(&mark->refcnt) < 2);
--
- spin_lock(&group->mark_lock);
-
- if (mark->flags & FSNOTIFY_MARK_FLAG_INODE) {
-@@ -182,6 +179,11 @@ void fsnotify_destroy_mark(struct fsnotify_mark *mark)
- iput(inode);
-
- /*
-+ * We don't necessarily have a ref on mark from caller so the above iput
-+ * may have already destroyed it. Don't touch from now on.
-+ */
-+
-+ /*
- * it's possible that this group tried to destroy itself, but this
- * this mark was simultaneously being freed by inode. If that's the
- * case, we finish freeing the group here.
diff --git a/fs/notify/notification.c b/fs/notify/notification.c
index ee18815..7aa5d01 100644
--- a/fs/notify/notification.c
@@ -45395,7 +45196,7 @@ index 3a1dafd..d41fc37 100644
+}
+#endif
diff --git a/fs/proc/base.c b/fs/proc/base.c
-index 851ba3d..813fd0b 100644
+index 1fc1dca..813fd0b 100644
--- a/fs/proc/base.c
+++ b/fs/proc/base.c
@@ -107,6 +107,22 @@ struct pid_entry {
@@ -45421,79 +45222,12 @@ index 851ba3d..813fd0b 100644
#define NOD(NAME, MODE, IOP, FOP, OP) { \
.name = (NAME), \
.len = sizeof(NAME) - 1, \
-@@ -194,65 +210,7 @@ static int proc_root_link(struct inode *inode, struct path *path)
- return result;
- }
-
--static struct mm_struct *__check_mem_permission(struct task_struct *task)
--{
-- struct mm_struct *mm;
--
-- mm = get_task_mm(task);
-- if (!mm)
-- return ERR_PTR(-EINVAL);
--
-- /*
-- * A task can always look at itself, in case it chooses
-- * to use system calls instead of load instructions.
-- */
-- if (task == current)
-- return mm;
--
-- /*
-- * If current is actively ptrace'ing, and would also be
-- * permitted to freshly attach with ptrace now, permit it.
-- */
-- if (task_is_stopped_or_traced(task)) {
-- int match;
-- rcu_read_lock();
-- match = (ptrace_parent(task) == current);
-- rcu_read_unlock();
-- if (match && ptrace_may_access(task, PTRACE_MODE_ATTACH))
-- return mm;
-- }
--
-- /*
-- * No one else is allowed.
-- */
-- mmput(mm);
-- return ERR_PTR(-EPERM);
--}
--
--/*
-- * If current may access user memory in @task return a reference to the
-- * corresponding mm, otherwise ERR_PTR.
-- */
--static struct mm_struct *check_mem_permission(struct task_struct *task)
--{
-- struct mm_struct *mm;
-- int err;
--
-- /*
-- * Avoid racing if task exec's as we might get a new mm but validate
-- * against old credentials.
-- */
-- err = mutex_lock_killable(&task->signal->cred_guard_mutex);
-- if (err)
-- return ERR_PTR(err);
--
-- mm = __check_mem_permission(task);
-- mutex_unlock(&task->signal->cred_guard_mutex);
--
-- return mm;
--}
--
--struct mm_struct *mm_for_maps(struct task_struct *task)
-+static struct mm_struct *mm_access(struct task_struct *task, unsigned int mode)
- {
- struct mm_struct *mm;
- int err;
-@@ -262,16 +220,23 @@ struct mm_struct *mm_for_maps(struct task_struct *task)
+@@ -204,10 +220,12 @@ static struct mm_struct *mm_access(struct task_struct *task, unsigned int mode)
return ERR_PTR(err);
mm = get_task_mm(task);
- if (mm && mm != current->mm &&
-- !ptrace_may_access(task, PTRACE_MODE_READ)) {
+- !ptrace_may_access(task, mode)) {
- mmput(mm);
- mm = ERR_PTR(-EACCES);
+ if (mm) {
@@ -45505,18 +45239,7 @@ index 851ba3d..813fd0b 100644
}
mutex_unlock(&task->signal->cred_guard_mutex);
- return mm;
- }
-
-+struct mm_struct *mm_for_maps(struct task_struct *task)
-+{
-+ return mm_access(task, PTRACE_MODE_READ);
-+}
-+
- static int proc_pid_cmdline(struct task_struct *task, char * buffer)
- {
- int res = 0;
-@@ -282,6 +247,9 @@ static int proc_pid_cmdline(struct task_struct *task, char * buffer)
+@@ -229,6 +247,9 @@ static int proc_pid_cmdline(struct task_struct *task, char * buffer)
if (!mm->arg_end)
goto out_mm; /* Shh! No looking before we're done */
@@ -45526,7 +45249,7 @@ index 851ba3d..813fd0b 100644
len = mm->arg_end - mm->arg_start;
if (len > PAGE_SIZE)
-@@ -309,12 +277,28 @@ out:
+@@ -256,12 +277,28 @@ out:
return res;
}
@@ -45555,7 +45278,7 @@ index 851ba3d..813fd0b 100644
do {
nwords += 2;
} while (mm->saved_auxv[nwords - 2] != 0); /* AT_NULL */
-@@ -328,7 +312,7 @@ static int proc_pid_auxv(struct task_struct *task, char *buffer)
+@@ -275,7 +312,7 @@ static int proc_pid_auxv(struct task_struct *task, char *buffer)
}
@@ -45564,7 +45287,7 @@ index 851ba3d..813fd0b 100644
/*
* Provides a wchan file via kallsyms in a proper one-value-per-file format.
* Returns the resolved symbol. If that fails, simply return the address.
-@@ -367,7 +351,7 @@ static void unlock_trace(struct task_struct *task)
+@@ -314,7 +351,7 @@ static void unlock_trace(struct task_struct *task)
mutex_unlock(&task->signal->cred_guard_mutex);
}
@@ -45573,7 +45296,7 @@ index 851ba3d..813fd0b 100644
#define MAX_STACK_TRACE_DEPTH 64
-@@ -558,7 +542,7 @@ static int proc_pid_limits(struct task_struct *task, char *buffer)
+@@ -505,7 +542,7 @@ static int proc_pid_limits(struct task_struct *task, char *buffer)
return count;
}
@@ -45582,7 +45305,7 @@ index 851ba3d..813fd0b 100644
static int proc_pid_syscall(struct task_struct *task, char *buffer)
{
long nr;
-@@ -587,7 +571,7 @@ static int proc_pid_syscall(struct task_struct *task, char *buffer)
+@@ -534,7 +571,7 @@ static int proc_pid_syscall(struct task_struct *task, char *buffer)
/************************************************************************/
/* permission checks */
@@ -45591,7 +45314,7 @@ index 851ba3d..813fd0b 100644
{
struct task_struct *task;
int allowed = 0;
-@@ -597,7 +581,10 @@ static int proc_fd_access_allowed(struct inode *inode)
+@@ -544,7 +581,10 @@ static int proc_fd_access_allowed(struct inode *inode)
*/
task = get_proc_task(inode);
if (task) {
@@ -45603,75 +45326,7 @@ index 851ba3d..813fd0b 100644
put_task_struct(task);
}
return allowed;
-@@ -816,38 +803,39 @@ static const struct file_operations proc_single_file_operations = {
-
- static int mem_open(struct inode* inode, struct file* file)
- {
-- file->private_data = (void*)((long)current->self_exec_id);
-+ struct task_struct *task = get_proc_task(file->f_path.dentry->d_inode);
-+ struct mm_struct *mm;
-+
-+ if (!task)
-+ return -ESRCH;
-+
-+ mm = mm_access(task, PTRACE_MODE_ATTACH);
-+ put_task_struct(task);
-+
-+ if (IS_ERR(mm))
-+ return PTR_ERR(mm);
-+
- /* OK to pass negative loff_t, we can catch out-of-range */
- file->f_mode |= FMODE_UNSIGNED_OFFSET;
-+ file->private_data = mm;
-+
- return 0;
- }
-
- static ssize_t mem_read(struct file * file, char __user * buf,
- size_t count, loff_t *ppos)
- {
-- struct task_struct *task = get_proc_task(file->f_path.dentry->d_inode);
-+ int ret;
- char *page;
- unsigned long src = *ppos;
-- int ret = -ESRCH;
-- struct mm_struct *mm;
-+ struct mm_struct *mm = file->private_data;
-
-- if (!task)
-- goto out_no_task;
-+ if (!mm)
-+ return 0;
-
-- ret = -ENOMEM;
- page = (char *)__get_free_page(GFP_TEMPORARY);
- if (!page)
-- goto out;
--
-- mm = check_mem_permission(task);
-- ret = PTR_ERR(mm);
-- if (IS_ERR(mm))
-- goto out_free;
--
-- ret = -EIO;
--
-- if (file->private_data != (void*)((long)current->self_exec_id))
-- goto out_put;
-+ return -ENOMEM;
-
- ret = 0;
-
-@@ -874,42 +862,28 @@ static ssize_t mem_read(struct file * file, char __user * buf,
- }
- *ppos = src;
-
--out_put:
-- mmput(mm);
--out_free:
- free_page((unsigned long) page);
--out:
-- put_task_struct(task);
--out_no_task:
+@@ -826,6 +866,10 @@ static ssize_t mem_read(struct file * file, char __user * buf,
return ret;
}
@@ -45682,75 +45337,15 @@ index 851ba3d..813fd0b 100644
static ssize_t mem_write(struct file * file, const char __user *buf,
size_t count, loff_t *ppos)
{
- int copied;
- char *page;
-- struct task_struct *task = get_proc_task(file->f_path.dentry->d_inode);
- unsigned long dst = *ppos;
-- struct mm_struct *mm;
-+ struct mm_struct *mm = file->private_data;
-
-- copied = -ESRCH;
-- if (!task)
-- goto out_no_task;
-+ if (!mm)
-+ return 0;
-
-- copied = -ENOMEM;
- page = (char *)__get_free_page(GFP_TEMPORARY);
- if (!page)
-- goto out_task;
--
-- mm = check_mem_permission(task);
-- copied = PTR_ERR(mm);
-- if (IS_ERR(mm))
-- goto out_free;
--
-- copied = -EIO;
-- if (file->private_data != (void *)((long)current->self_exec_id))
-- goto out_mm;
-+ return -ENOMEM;
-
- copied = 0;
- while (count > 0) {
-@@ -933,15 +907,10 @@ static ssize_t mem_write(struct file * file, const char __user *buf,
- }
- *ppos = dst;
-
--out_mm:
-- mmput(mm);
--out_free:
+@@ -866,6 +910,7 @@ static ssize_t mem_write(struct file * file, const char __user *buf,
free_page((unsigned long) page);
--out_task:
-- put_task_struct(task);
--out_no_task:
return copied;
}
+#endif
loff_t mem_lseek(struct file *file, loff_t offset, int orig)
{
-@@ -959,11 +928,20 @@ loff_t mem_lseek(struct file *file, loff_t offset, int orig)
- return file->f_pos;
- }
-
-+static int mem_release(struct inode *inode, struct file *file)
-+{
-+ struct mm_struct *mm = file->private_data;
-+
-+ mmput(mm);
-+ return 0;
-+}
-+
- static const struct file_operations proc_mem_operations = {
- .llseek = mem_lseek,
- .read = mem_read,
- .write = mem_write,
- .open = mem_open,
-+ .release = mem_release,
- };
-
- static ssize_t environ_read(struct file *file, char __user *buf,
-@@ -978,6 +956,9 @@ static ssize_t environ_read(struct file *file, char __user *buf,
+@@ -911,6 +956,9 @@ static ssize_t environ_read(struct file *file, char __user *buf,
if (!task)
goto out_no_task;
@@ -45760,7 +45355,7 @@ index 851ba3d..813fd0b 100644
ret = -ENOMEM;
page = (char *)__get_free_page(GFP_TEMPORARY);
if (!page)
-@@ -1600,7 +1581,7 @@ static void *proc_pid_follow_link(struct dentry *dentry, struct nameidata *nd)
+@@ -1533,7 +1581,7 @@ static void *proc_pid_follow_link(struct dentry *dentry, struct nameidata *nd)
path_put(&nd->path);
/* Are we allowed to snoop on the tasks file descriptors? */
@@ -45769,7 +45364,7 @@ index 851ba3d..813fd0b 100644
goto out;
error = PROC_I(inode)->op.proc_get_link(inode, &nd->path);
-@@ -1639,8 +1620,18 @@ static int proc_pid_readlink(struct dentry * dentry, char __user * buffer, int b
+@@ -1572,8 +1620,18 @@ static int proc_pid_readlink(struct dentry * dentry, char __user * buffer, int b
struct path path;
/* Are we allowed to snoop on the tasks file descriptors? */
@@ -45790,7 +45385,7 @@ index 851ba3d..813fd0b 100644
error = PROC_I(inode)->op.proc_get_link(inode, &path);
if (error)
-@@ -1705,7 +1696,11 @@ struct inode *proc_pid_make_inode(struct super_block * sb, struct task_struct *t
+@@ -1638,7 +1696,11 @@ struct inode *proc_pid_make_inode(struct super_block * sb, struct task_struct *t
rcu_read_lock();
cred = __task_cred(task);
inode->i_uid = cred->euid;
@@ -45802,7 +45397,7 @@ index 851ba3d..813fd0b 100644
rcu_read_unlock();
}
security_task_to_inode(task, inode);
-@@ -1723,6 +1718,9 @@ int pid_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
+@@ -1656,6 +1718,9 @@ int pid_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
struct inode *inode = dentry->d_inode;
struct task_struct *task;
const struct cred *cred;
@@ -45812,7 +45407,7 @@ index 851ba3d..813fd0b 100644
generic_fillattr(inode, stat);
-@@ -1730,13 +1728,41 @@ int pid_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
+@@ -1663,13 +1728,41 @@ int pid_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
stat->uid = 0;
stat->gid = 0;
task = pid_task(proc_pid(inode), PIDTYPE_PID);
@@ -45855,7 +45450,7 @@ index 851ba3d..813fd0b 100644
}
rcu_read_unlock();
return 0;
-@@ -1773,11 +1799,20 @@ int pid_revalidate(struct dentry *dentry, struct nameidata *nd)
+@@ -1706,11 +1799,20 @@ int pid_revalidate(struct dentry *dentry, struct nameidata *nd)
if (task) {
if ((inode->i_mode == (S_IFDIR|S_IRUGO|S_IXUGO)) ||
@@ -45876,7 +45471,7 @@ index 851ba3d..813fd0b 100644
rcu_read_unlock();
} else {
inode->i_uid = 0;
-@@ -1895,7 +1930,8 @@ static int proc_fd_info(struct inode *inode, struct path *path, char *info)
+@@ -1828,7 +1930,8 @@ static int proc_fd_info(struct inode *inode, struct path *path, char *info)
int fd = proc_fd(inode);
if (task) {
@@ -45886,7 +45481,7 @@ index 851ba3d..813fd0b 100644
put_task_struct(task);
}
if (files) {
-@@ -2163,11 +2199,21 @@ static const struct file_operations proc_fd_operations = {
+@@ -2096,11 +2199,21 @@ static const struct file_operations proc_fd_operations = {
*/
static int proc_fd_permission(struct inode *inode, int mask)
{
@@ -45910,7 +45505,7 @@ index 851ba3d..813fd0b 100644
return rv;
}
-@@ -2277,6 +2323,9 @@ static struct dentry *proc_pident_lookup(struct inode *dir,
+@@ -2210,6 +2323,9 @@ static struct dentry *proc_pident_lookup(struct inode *dir,
if (!task)
goto out_no_task;
@@ -45920,7 +45515,7 @@ index 851ba3d..813fd0b 100644
/*
* Yes, it does not scale. And it should not. Don't add
* new entries into /proc/<tgid>/ without very good reasons.
-@@ -2321,6 +2370,9 @@ static int proc_pident_readdir(struct file *filp,
+@@ -2254,6 +2370,9 @@ static int proc_pident_readdir(struct file *filp,
if (!task)
goto out_no_task;
@@ -45930,7 +45525,7 @@ index 851ba3d..813fd0b 100644
ret = 0;
i = filp->f_pos;
switch (i) {
-@@ -2591,7 +2643,7 @@ static void *proc_self_follow_link(struct dentry *dentry, struct nameidata *nd)
+@@ -2524,7 +2643,7 @@ static void *proc_self_follow_link(struct dentry *dentry, struct nameidata *nd)
static void proc_self_put_link(struct dentry *dentry, struct nameidata *nd,
void *cookie)
{
@@ -45939,7 +45534,7 @@ index 851ba3d..813fd0b 100644
if (!IS_ERR(s))
__putname(s);
}
-@@ -2789,7 +2841,7 @@ static const struct pid_entry tgid_base_stuff[] = {
+@@ -2722,7 +2841,7 @@ static const struct pid_entry tgid_base_stuff[] = {
REG("autogroup", S_IRUGO|S_IWUSR, proc_pid_sched_autogroup_operations),
#endif
REG("comm", S_IRUGO|S_IWUSR, proc_pid_set_comm_operations),
@@ -45948,7 +45543,7 @@ index 851ba3d..813fd0b 100644
INF("syscall", S_IRUGO, proc_pid_syscall),
#endif
INF("cmdline", S_IRUGO, proc_pid_cmdline),
-@@ -2814,10 +2866,10 @@ static const struct pid_entry tgid_base_stuff[] = {
+@@ -2747,10 +2866,10 @@ static const struct pid_entry tgid_base_stuff[] = {
#ifdef CONFIG_SECURITY
DIR("attr", S_IRUGO|S_IXUGO, proc_attr_dir_inode_operations, proc_attr_dir_operations),
#endif
@@ -45961,7 +45556,7 @@ index 851ba3d..813fd0b 100644
ONE("stack", S_IRUGO, proc_pid_stack),
#endif
#ifdef CONFIG_SCHEDSTATS
-@@ -2851,6 +2903,9 @@ static const struct pid_entry tgid_base_stuff[] = {
+@@ -2784,6 +2903,9 @@ static const struct pid_entry tgid_base_stuff[] = {
#ifdef CONFIG_HARDWALL
INF("hardwall", S_IRUGO, proc_pid_hardwall),
#endif
@@ -45971,7 +45566,7 @@ index 851ba3d..813fd0b 100644
};
static int proc_tgid_base_readdir(struct file * filp,
-@@ -2976,7 +3031,14 @@ static struct dentry *proc_pid_instantiate(struct inode *dir,
+@@ -2909,7 +3031,14 @@ static struct dentry *proc_pid_instantiate(struct inode *dir,
if (!inode)
goto out;
@@ -45986,7 +45581,7 @@ index 851ba3d..813fd0b 100644
inode->i_op = &proc_tgid_base_inode_operations;
inode->i_fop = &proc_tgid_base_operations;
inode->i_flags|=S_IMMUTABLE;
-@@ -3018,7 +3080,11 @@ struct dentry *proc_pid_lookup(struct inode *dir, struct dentry * dentry, struct
+@@ -2951,7 +3080,11 @@ struct dentry *proc_pid_lookup(struct inode *dir, struct dentry * dentry, struct
if (!task)
goto out;
@@ -45998,7 +45593,7 @@ index 851ba3d..813fd0b 100644
put_task_struct(task);
out:
return result;
-@@ -3083,6 +3149,11 @@ int proc_pid_readdir(struct file * filp, void * dirent, filldir_t filldir)
+@@ -3016,6 +3149,11 @@ int proc_pid_readdir(struct file * filp, void * dirent, filldir_t filldir)
{
unsigned int nr;
struct task_struct *reaper;
@@ -46010,7 +45605,7 @@ index 851ba3d..813fd0b 100644
struct tgid_iter iter;
struct pid_namespace *ns;
-@@ -3106,8 +3177,27 @@ int proc_pid_readdir(struct file * filp, void * dirent, filldir_t filldir)
+@@ -3039,8 +3177,27 @@ int proc_pid_readdir(struct file * filp, void * dirent, filldir_t filldir)
for (iter = next_tgid(ns, iter);
iter.task;
iter.tgid += 1, iter = next_tgid(ns, iter)) {
@@ -46039,7 +45634,7 @@ index 851ba3d..813fd0b 100644
put_task_struct(iter.task);
goto out;
}
-@@ -3135,7 +3225,7 @@ static const struct pid_entry tid_base_stuff[] = {
+@@ -3068,7 +3225,7 @@ static const struct pid_entry tid_base_stuff[] = {
REG("sched", S_IRUGO|S_IWUSR, proc_pid_sched_operations),
#endif
REG("comm", S_IRUGO|S_IWUSR, proc_pid_set_comm_operations),
@@ -46048,7 +45643,7 @@ index 851ba3d..813fd0b 100644
INF("syscall", S_IRUGO, proc_pid_syscall),
#endif
INF("cmdline", S_IRUGO, proc_pid_cmdline),
-@@ -3159,10 +3249,10 @@ static const struct pid_entry tid_base_stuff[] = {
+@@ -3092,10 +3249,10 @@ static const struct pid_entry tid_base_stuff[] = {
#ifdef CONFIG_SECURITY
DIR("attr", S_IRUGO|S_IXUGO, proc_attr_dir_inode_operations, proc_attr_dir_operations),
#endif
@@ -46267,7 +45862,7 @@ index f738024..876984a 100644
rcu_read_lock();
task = pid_task(proc_pid(dir), PIDTYPE_PID);
diff --git a/fs/proc/proc_sysctl.c b/fs/proc/proc_sysctl.c
-index a6b6217..3d0953c 100644
+index a6b6217..1e0579d 100644
--- a/fs/proc/proc_sysctl.c
+++ b/fs/proc/proc_sysctl.c
@@ -9,11 +9,13 @@
@@ -46301,7 +45896,20 @@ index a6b6217..3d0953c 100644
out:
sysctl_head_finish(head);
return err;
-@@ -245,6 +253,9 @@ static int proc_sys_fill_cache(struct file *filp, void *dirent,
+@@ -163,6 +171,12 @@ static ssize_t proc_sys_call_handler(struct file *filp, void __user *buf,
+ if (!table->proc_handler)
+ goto out;
+
++#ifdef CONFIG_GRKERNSEC
++ error = -EPERM;
++ if (write && !capable(CAP_SYS_ADMIN))
++ goto out;
++#endif
++
+ /* careful: calling conventions are nasty here */
+ res = count;
+ error = table->proc_handler(table, write, buf, &res, ppos);
+@@ -245,6 +259,9 @@ static int proc_sys_fill_cache(struct file *filp, void *dirent,
return -ENOMEM;
} else {
d_set_d_op(child, &proc_sys_dentry_operations);
@@ -46311,7 +45919,7 @@ index a6b6217..3d0953c 100644
d_add(child, inode);
}
} else {
-@@ -273,6 +284,9 @@ static int scan(struct ctl_table_header *head, ctl_table *table,
+@@ -273,6 +290,9 @@ static int scan(struct ctl_table_header *head, ctl_table *table,
if (*pos < file->f_pos)
continue;
@@ -46321,7 +45929,7 @@ index a6b6217..3d0953c 100644
res = proc_sys_fill_cache(file, dirent, filldir, head, table);
if (res)
return res;
-@@ -398,6 +412,9 @@ static int proc_sys_getattr(struct vfsmount *mnt, struct dentry *dentry, struct
+@@ -398,6 +418,9 @@ static int proc_sys_getattr(struct vfsmount *mnt, struct dentry *dentry, struct
if (IS_ERR(head))
return PTR_ERR(head);
@@ -46331,7 +45939,7 @@ index a6b6217..3d0953c 100644
generic_fillattr(inode, stat);
if (table)
stat->mode = (stat->mode & S_IFMT) | table->mode;
-@@ -420,13 +437,13 @@ static const struct file_operations proc_sys_dir_file_operations = {
+@@ -420,13 +443,13 @@ static const struct file_operations proc_sys_dir_file_operations = {
.llseek = generic_file_llseek,
};
@@ -46368,7 +45976,7 @@ index 03102d9..4ae347e 100644
}
diff --git a/fs/proc/task_mmu.c b/fs/proc/task_mmu.c
-index e418c5a..e66a99c 100644
+index 7dcd2a2..d1d9cb6 100644
--- a/fs/proc/task_mmu.c
+++ b/fs/proc/task_mmu.c
@@ -52,8 +52,13 @@ void task_mem(struct seq_file *m, struct mm_struct *mm)
@@ -46501,7 +46109,7 @@ index e418c5a..e66a99c 100644
mss.resident >> 10,
(unsigned long)(mss.pss >> (10 + PSS_SHIFT)),
mss.shared_clean >> 10,
-@@ -1033,7 +1064,7 @@ static int show_numa_map(struct seq_file *m, void *v)
+@@ -1036,7 +1067,7 @@ static int show_numa_map(struct seq_file *m, void *v)
if (file) {
seq_printf(m, " file=");
@@ -47156,10 +46764,10 @@ index 23ce927..e274cc1 100644
kfree(s);
diff --git a/grsecurity/Kconfig b/grsecurity/Kconfig
new file mode 100644
-index 0000000..4639511
+index 0000000..fbe6950d9
--- /dev/null
+++ b/grsecurity/Kconfig
-@@ -0,0 +1,1051 @@
+@@ -0,0 +1,1067 @@
+#
+# grecurity configuration
+#
@@ -47298,6 +46906,7 @@ index 0000000..4639511
+ select GRKERNSEC_AUDIT_MOUNT
+ select GRKERNSEC_MODHARDEN if (MODULES)
+ select GRKERNSEC_HARDEN_PTRACE
++ select GRKERNSEC_PTRACE_READEXEC
+ select GRKERNSEC_VM86 if (X86_32)
+ select GRKERNSEC_KERN_LOCKOUT if (X86 || ARM || PPC || SPARC)
+ select PAX
@@ -47960,6 +47569,21 @@ index 0000000..4639511
+ option is enabled, a sysctl option with name "harden_ptrace" is
+ created.
+
++config GRKERNSEC_PTRACE_READEXEC
++ bool "Require read access to ptrace sensitive binaries"
++ help
++ If you say Y here, read permission will be required by any unprivileged
++ process to ptrace suid/sgid binaries. Note that the ability to
++ ptrace privileged binaries and retain that binary's privilege is
++ already not possible. This option is useful in environments that
++ remove the read bits (e.g. file mode 4711) from suid binaries to
++ prevent infoleaking of their contents. What this option adds
++ is consistency to the use of that file mode, as the binary could normally
++ be read out when run without privileges while ptracing.
++
++ If the sysctl option is enabled, a sysctl option with name "ptrace_readexec"
++ is created.
++
+config GRKERNSEC_SETXID
+ bool "Enforce consistent multithreaded privileges"
+ help
@@ -55137,10 +54761,10 @@ index 0000000..8ca18bf
+}
diff --git a/grsecurity/grsec_init.c b/grsecurity/grsec_init.c
new file mode 100644
-index 0000000..cb8e5a1
+index 0000000..01ddde4
--- /dev/null
+++ b/grsecurity/grsec_init.c
-@@ -0,0 +1,273 @@
+@@ -0,0 +1,277 @@
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/mm.h>
@@ -55150,6 +54774,7 @@ index 0000000..cb8e5a1
+#include <linux/percpu.h>
+#include <linux/module.h>
+
++int grsec_enable_ptrace_readexec;
+int grsec_enable_setxid;
+int grsec_enable_brute;
+int grsec_enable_link;
@@ -55303,6 +54928,9 @@ index 0000000..cb8e5a1
+ grsec_enable_group = 1;
+ grsec_audit_gid = CONFIG_GRKERNSEC_AUDIT_GID;
+#endif
++#ifdef CONFIG_GRKERNSEC_PTRACE_READEXEC
++ grsec_enable_ptrace_readexec = 1;
++#endif
+#ifdef CONFIG_GRKERNSEC_AUDIT_CHDIR
+ grsec_enable_chdir = 1;
+#endif
@@ -55942,14 +55570,14 @@ index 0000000..a3b12a0
+}
diff --git a/grsecurity/grsec_ptrace.c b/grsecurity/grsec_ptrace.c
new file mode 100644
-index 0000000..472c1d6
+index 0000000..f7f29aa
--- /dev/null
+++ b/grsecurity/grsec_ptrace.c
-@@ -0,0 +1,14 @@
+@@ -0,0 +1,30 @@
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/grinternal.h>
-+#include <linux/grsecurity.h>
++#include <linux/security.h>
+
+void
+gr_audit_ptrace(struct task_struct *task)
@@ -55960,6 +55588,22 @@ index 0000000..472c1d6
+#endif
+ return;
+}
++
++int
++gr_ptrace_readexec(struct file *file, int unsafe_flags)
++{
++#ifdef CONFIG_GRKERNSEC_PTRACE_READEXEC
++ const struct dentry *dentry = file->f_path.dentry;
++ const struct vfsmount *mnt = file->f_path.mnt;
++
++ if (grsec_enable_ptrace_readexec && (unsafe_flags & LSM_UNSAFE_PTRACE) &&
++ (inode_permission(dentry->d_inode, MAY_READ) || !gr_acl_handle_open(dentry, mnt, MAY_READ))) {
++ gr_log_fs_generic(GR_DONT_AUDIT, GR_PTRACE_READEXEC_MSG, dentry, mnt);
++ return -EACCES;
++ }
++#endif
++ return 0;
++}
diff --git a/grsecurity/grsec_sig.c b/grsecurity/grsec_sig.c
new file mode 100644
index 0000000..7a5b2de
@@ -56425,10 +56069,10 @@ index 0000000..4030d57
+}
diff --git a/grsecurity/grsec_sysctl.c b/grsecurity/grsec_sysctl.c
new file mode 100644
-index 0000000..bceef2f
+index 0000000..a1aedd7
--- /dev/null
+++ b/grsecurity/grsec_sysctl.c
-@@ -0,0 +1,442 @@
+@@ -0,0 +1,451 @@
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/sysctl.h>
@@ -56492,6 +56136,15 @@ index 0000000..bceef2f
+ .proc_handler = &proc_dointvec,
+ },
+#endif
++#ifdef CONFIG_GRKERNSEC_PTRACE_READEXEC
++ {
++ .procname = "ptrace_readexec",
++ .data = &grsec_enable_ptrace_readexec,
++ .maxlen = sizeof(int),
++ .mode = 0600,
++ .proc_handler = &proc_dointvec,
++ },
++#endif
+#ifdef CONFIG_GRKERNSEC_SETXID
+ {
+ .procname = "consistent_setxid",
@@ -57645,20 +57298,10 @@ index fd88a39..f4d0bad 100644
};
diff --git a/include/linux/blkdev.h b/include/linux/blkdev.h
-index 94acd81..3ab569b 100644
+index 0ed1eb0..3ab569b 100644
--- a/include/linux/blkdev.h
+++ b/include/linux/blkdev.h
-@@ -675,6 +675,9 @@ extern int blk_insert_cloned_request(struct request_queue *q,
- struct request *rq);
- extern void blk_delay_queue(struct request_queue *, unsigned long);
- extern void blk_recount_segments(struct request_queue *, struct bio *);
-+extern int scsi_verify_blk_ioctl(struct block_device *, unsigned int);
-+extern int scsi_cmd_blk_ioctl(struct block_device *, fmode_t,
-+ unsigned int, void __user *);
- extern int scsi_cmd_ioctl(struct request_queue *, struct gendisk *, fmode_t,
- unsigned int, void __user *);
- extern int sg_scsi_ioctl(struct request_queue *, struct gendisk *, fmode_t,
-@@ -1312,7 +1315,7 @@ struct block_device_operations {
+@@ -1315,7 +1315,7 @@ struct block_device_operations {
/* this callback is with swap_lock and sometimes page table lock held */
void (*swap_slot_free_notify) (struct block_device *, unsigned long);
struct module *owner;
@@ -58744,10 +58387,10 @@ index 0000000..b30e9bc
+#endif
diff --git a/include/linux/grinternal.h b/include/linux/grinternal.h
new file mode 100644
-index 0000000..60cda84
+index 0000000..da390f1
--- /dev/null
+++ b/include/linux/grinternal.h
-@@ -0,0 +1,220 @@
+@@ -0,0 +1,221 @@
+#ifndef __GRINTERNAL_H
+#define __GRINTERNAL_H
+
@@ -58784,6 +58427,7 @@ index 0000000..60cda84
+char *gr_to_filename3(const struct dentry *dentry,
+ const struct vfsmount *mnt);
+
++extern int grsec_enable_ptrace_readexec;
+extern int grsec_enable_harden_ptrace;
+extern int grsec_enable_link;
+extern int grsec_enable_fifo;
@@ -58970,10 +58614,10 @@ index 0000000..60cda84
+#endif
diff --git a/include/linux/grmsg.h b/include/linux/grmsg.h
new file mode 100644
-index 0000000..9d5fd4a
+index 0000000..cf49370
--- /dev/null
+++ b/include/linux/grmsg.h
-@@ -0,0 +1,108 @@
+@@ -0,0 +1,109 @@
+#define DEFAULTSECMSG "%.256s[%.16s:%d] uid/euid:%u/%u gid/egid:%u/%u, parent %.256s[%.16s:%d] uid/euid:%u/%u gid/egid:%u/%u"
+#define GR_ACL_PROCACCT_MSG "%.256s[%.16s:%d] IP:%pI4 TTY:%.64s uid/euid:%u/%u gid/egid:%u/%u run time:[%ud %uh %um %us] cpu time:[%ud %uh %um %us] %s with exit code %ld, parent %.256s[%.16s:%d] IP:%pI4 TTY:%.64s uid/euid:%u/%u gid/egid:%u/%u"
+#define GR_PTRACE_ACL_MSG "denied ptrace of %.950s(%.16s:%d) by "
@@ -59081,13 +58725,14 @@ index 0000000..9d5fd4a
+#define GR_TEXTREL_AUDIT_MSG "text relocation in %s, VMA:0x%08lx 0x%08lx by "
+#define GR_VM86_MSG "denied use of vm86 by "
+#define GR_PTRACE_AUDIT_MSG "process %.950s(%.16s:%d) attached to via ptrace by "
++#define GR_PTRACE_READEXEC_MSG "denied ptrace of unreadable suid/sgid binary %.950s by "
+#define GR_INIT_TRANSFER_MSG "persistent special role transferred privilege to init by "
diff --git a/include/linux/grsecurity.h b/include/linux/grsecurity.h
new file mode 100644
-index 0000000..4620f36
+index 0000000..1ca3931
--- /dev/null
+++ b/include/linux/grsecurity.h
-@@ -0,0 +1,231 @@
+@@ -0,0 +1,233 @@
+#ifndef GR_SECURITY_H
+#define GR_SECURITY_H
+#include <linux/fs.h>
@@ -59303,6 +58948,8 @@ index 0000000..4620f36
+void gr_audit_ptrace(struct task_struct *task);
+dev_t gr_get_dev_from_dentry(struct dentry *dentry);
+
++int gr_ptrace_readexec(struct file *file, int unsafe_flags);
++
+#ifdef CONFIG_GRKERNSEC
+void task_grsec_rbac(struct seq_file *m, struct task_struct *p);
+void gr_handle_vm86(void);
@@ -61823,10 +61470,10 @@ index 444cd6b..3327cc5 100644
const struct firmware *dsp_microcode;
const struct firmware *controller_microcode;
diff --git a/include/target/target_core_base.h b/include/target/target_core_base.h
-index 6873c7d..b1e8009 100644
+index a79886c..b483af6 100644
--- a/include/target/target_core_base.h
+++ b/include/target/target_core_base.h
-@@ -345,7 +345,7 @@ struct t10_reservation_ops {
+@@ -346,7 +346,7 @@ struct t10_reservation_ops {
int (*t10_seq_non_holder)(struct se_cmd *, unsigned char *, u32);
int (*t10_pr_register)(struct se_cmd *);
int (*t10_pr_clear)(struct se_cmd *);
@@ -61835,7 +61482,7 @@ index 6873c7d..b1e8009 100644
struct t10_reservation {
/* Reservation effects all target ports */
-@@ -464,8 +464,8 @@ struct se_cmd {
+@@ -465,8 +465,8 @@ struct se_cmd {
atomic_t t_se_count;
atomic_t t_task_cdbs_left;
atomic_t t_task_cdbs_ex_left;
@@ -61846,7 +61493,7 @@ index 6873c7d..b1e8009 100644
atomic_t t_transport_active;
atomic_t t_transport_complete;
atomic_t t_transport_queue_active;
-@@ -703,7 +703,7 @@ struct se_device {
+@@ -704,7 +704,7 @@ struct se_device {
/* Active commands on this virtual SE device */
atomic_t simple_cmds;
atomic_t depth_left;
@@ -61922,7 +61569,7 @@ index 43298f9..2f56c12 100644
Randomizing heap placement makes heap exploits harder, but it
also breaks ancient binaries (including anything libc5 based).
diff --git a/init/do_mounts.c b/init/do_mounts.c
-index 0f6e1d9..89d0af4 100644
+index db6e5ee..7677ff7 100644
--- a/init/do_mounts.c
+++ b/init/do_mounts.c
@@ -325,11 +325,11 @@ static void __init get_fs_names(char *page)
@@ -61939,7 +61586,7 @@ index 0f6e1d9..89d0af4 100644
ROOT_DEV = current->fs->pwd.mnt->mnt_sb->s_dev;
printk(KERN_INFO
"VFS: Mounted root (%s filesystem)%s on device %u:%u.\n",
-@@ -421,18 +421,18 @@ void __init change_floppy(char *fmt, ...)
+@@ -448,18 +448,18 @@ void __init change_floppy(char *fmt, ...)
va_start(args, fmt);
vsprintf(buf, fmt, args);
va_end(args);
@@ -61961,7 +61608,7 @@ index 0f6e1d9..89d0af4 100644
termios.c_lflag |= ICANON;
sys_ioctl(fd, TCSETSF, (long)&termios);
sys_close(fd);
-@@ -526,6 +526,6 @@ void __init prepare_namespace(void)
+@@ -553,6 +553,6 @@ void __init prepare_namespace(void)
mount_root();
out:
devtmpfs_mount("dev");
@@ -62412,7 +62059,7 @@ index 5215a81..cfc0cac 100644
sem_params.flg = semflg;
sem_params.u.nsems = nsems;
diff --git a/ipc/shm.c b/ipc/shm.c
-index 02ecf2c..be05b1e 100644
+index b76be5b..859e750 100644
--- a/ipc/shm.c
+++ b/ipc/shm.c
@@ -69,6 +69,14 @@ static void shm_destroy (struct ipc_namespace *ns, struct shmid_kernel *shp);
@@ -62470,16 +62117,7 @@ index 02ecf2c..be05b1e 100644
shm_params.key = key;
shm_params.flg = shmflg;
shm_params.u.size = size;
-@@ -870,8 +887,6 @@ SYSCALL_DEFINE3(shmctl, int, shmid, int, cmd, struct shmid_ds __user *, buf)
- case SHM_LOCK:
- case SHM_UNLOCK:
- {
-- struct file *uninitialized_var(shm_file);
--
- lru_add_drain_all(); /* drain pagevecs to lru lists */
-
- shp = shm_lock_check(ns, shmid);
-@@ -981,6 +996,12 @@ long do_shmat(int shmid, char __user *shmaddr, int shmflg, ulong *raddr)
+@@ -988,6 +1005,12 @@ long do_shmat(int shmid, char __user *shmaddr, int shmflg, ulong *raddr)
f_mode = FMODE_READ | FMODE_WRITE;
}
if (shmflg & SHM_EXEC) {
@@ -62492,7 +62130,7 @@ index 02ecf2c..be05b1e 100644
prot |= PROT_EXEC;
acc_mode |= S_IXUGO;
}
-@@ -1004,9 +1025,21 @@ long do_shmat(int shmid, char __user *shmaddr, int shmflg, ulong *raddr)
+@@ -1011,9 +1034,21 @@ long do_shmat(int shmid, char __user *shmaddr, int shmflg, ulong *raddr)
if (err)
goto out_unlock;
@@ -63942,7 +63580,7 @@ index a4bea97..7a1ae9a 100644
/*
* If ret is 0, either ____call_usermodehelper failed and the
diff --git a/kernel/kprobes.c b/kernel/kprobes.c
-index e5d8464..4cc8cf0 100644
+index 52fd049..3def6a8 100644
--- a/kernel/kprobes.c
+++ b/kernel/kprobes.c
@@ -185,7 +185,7 @@ static kprobe_opcode_t __kprobes *__get_insn_slot(struct kprobe_insn_cache *c)
@@ -66872,7 +66510,7 @@ index 16fc34a..efd8bb8 100644
ret = -EIO;
bt->dropped_file = debugfs_create_file("dropped", 0444, dir, bt,
diff --git a/kernel/trace/ftrace.c b/kernel/trace/ftrace.c
-index b1e8943..369e4ff 100644
+index 25b4f4d..6f4772d 100644
--- a/kernel/trace/ftrace.c
+++ b/kernel/trace/ftrace.c
@@ -1587,12 +1587,17 @@ ftrace_code_disable(struct module *mod, struct dyn_ftrace *rec)
@@ -66895,7 +66533,7 @@ index b1e8943..369e4ff 100644
}
/*
-@@ -2609,7 +2614,7 @@ static void ftrace_free_entry_rcu(struct rcu_head *rhp)
+@@ -2608,7 +2613,7 @@ static void ftrace_free_entry_rcu(struct rcu_head *rhp)
int
register_ftrace_function_probe(char *glob, struct ftrace_probe_ops *ops,
@@ -67431,10 +67069,10 @@ index 011b110..b492af2 100644
from userspace allocation. Keeping a user from writing to low pages
can help reduce the impact of kernel NULL pointer bugs.
diff --git a/mm/filemap.c b/mm/filemap.c
-index 5f0a3c9..4f87f0c 100644
+index 90286a4..f441caa 100644
--- a/mm/filemap.c
+++ b/mm/filemap.c
-@@ -1784,7 +1784,7 @@ int generic_file_mmap(struct file * file, struct vm_area_struct * vma)
+@@ -1770,7 +1770,7 @@ int generic_file_mmap(struct file * file, struct vm_area_struct * vma)
struct address_space *mapping = file->f_mapping;
if (!mapping->a_ops->readpage)
@@ -67443,7 +67081,7 @@ index 5f0a3c9..4f87f0c 100644
file_accessed(file);
vma->vm_ops = &generic_file_vm_ops;
vma->vm_flags |= VM_CAN_NONLINEAR;
-@@ -2190,6 +2190,7 @@ inline int generic_write_checks(struct file *file, loff_t *pos, size_t *count, i
+@@ -2176,6 +2176,7 @@ inline int generic_write_checks(struct file *file, loff_t *pos, size_t *count, i
*pos = i_size_read(inode);
if (limit != RLIM_INFINITY) {
@@ -70236,7 +69874,7 @@ index b982290..7d73f53 100644
new->vm_region = region;
diff --git a/mm/page_alloc.c b/mm/page_alloc.c
-index 2b8ba3a..386d603 100644
+index 485be89..c059ad3 100644
--- a/mm/page_alloc.c
+++ b/mm/page_alloc.c
@@ -341,7 +341,7 @@ out:
@@ -70450,7 +70088,7 @@ index a4fd368..e0ffec7 100644
struct anon_vma_chain *avc;
struct anon_vma *anon_vma;
diff --git a/mm/shmem.c b/mm/shmem.c
-index d672250..2b233c1 100644
+index 6c253f7..367e20a 100644
--- a/mm/shmem.c
+++ b/mm/shmem.c
@@ -31,7 +31,7 @@
@@ -70471,7 +70109,7 @@ index d672250..2b233c1 100644
struct shmem_xattr {
struct list_head list; /* anchored by shmem_inode_info->xattr_list */
-@@ -2155,8 +2155,7 @@ int shmem_fill_super(struct super_block *sb, void *data, int silent)
+@@ -2180,8 +2180,7 @@ int shmem_fill_super(struct super_block *sb, void *data, int silent)
int err = -ENOMEM;
/* Round up to L1_CACHE_BYTES to resist false sharing */
@@ -71008,7 +70646,7 @@ index 8105be4..579da9d 100644
EXPORT_SYMBOL(kmem_cache_free);
diff --git a/mm/slub.c b/mm/slub.c
-index ed3334d..1739c9b 100644
+index 1a919f0..1739c9b 100644
--- a/mm/slub.c
+++ b/mm/slub.c
@@ -208,7 +208,7 @@ struct track {
@@ -71029,19 +70667,7 @@ index ed3334d..1739c9b 100644
s, (void *)t->addr, jiffies - t->when, t->cpu, t->pid);
#ifdef CONFIG_STACKTRACE
{
-@@ -2166,6 +2166,11 @@ redo:
- goto new_slab;
- }
-
-+ /* must check again c->freelist in case of cpu migration or IRQ */
-+ object = c->freelist;
-+ if (object)
-+ goto load_freelist;
-+
- stat(s, ALLOC_SLOWPATH);
-
- do {
-@@ -2554,6 +2559,8 @@ void kmem_cache_free(struct kmem_cache *s, void *x)
+@@ -2559,6 +2559,8 @@ void kmem_cache_free(struct kmem_cache *s, void *x)
page = virt_to_head_page(x);
@@ -71050,7 +70676,7 @@ index ed3334d..1739c9b 100644
slab_free(s, page, x, _RET_IP_);
trace_kmem_cache_free(_RET_IP_, x);
-@@ -2587,7 +2594,7 @@ static int slub_min_objects;
+@@ -2592,7 +2594,7 @@ static int slub_min_objects;
* Merge control. If this is set then no merging of slab caches will occur.
* (Could be removed. This was introduced to pacify the merge skeptics.)
*/
@@ -71059,7 +70685,7 @@ index ed3334d..1739c9b 100644
/*
* Calculate the order of allocation given an slab object size.
-@@ -3037,7 +3044,7 @@ static int kmem_cache_open(struct kmem_cache *s,
+@@ -3042,7 +3044,7 @@ static int kmem_cache_open(struct kmem_cache *s,
else
s->cpu_partial = 30;
@@ -71068,7 +70694,7 @@ index ed3334d..1739c9b 100644
#ifdef CONFIG_NUMA
s->remote_node_defrag_ratio = 1000;
#endif
-@@ -3141,8 +3148,7 @@ static inline int kmem_cache_close(struct kmem_cache *s)
+@@ -3146,8 +3148,7 @@ static inline int kmem_cache_close(struct kmem_cache *s)
void kmem_cache_destroy(struct kmem_cache *s)
{
down_write(&slub_lock);
@@ -71078,7 +70704,7 @@ index ed3334d..1739c9b 100644
list_del(&s->list);
up_write(&slub_lock);
if (kmem_cache_close(s)) {
-@@ -3353,6 +3359,50 @@ void *__kmalloc_node(size_t size, gfp_t flags, int node)
+@@ -3358,6 +3359,50 @@ void *__kmalloc_node(size_t size, gfp_t flags, int node)
EXPORT_SYMBOL(__kmalloc_node);
#endif
@@ -71129,7 +70755,7 @@ index ed3334d..1739c9b 100644
size_t ksize(const void *object)
{
struct page *page;
-@@ -3627,7 +3677,7 @@ static void __init kmem_cache_bootstrap_fixup(struct kmem_cache *s)
+@@ -3632,7 +3677,7 @@ static void __init kmem_cache_bootstrap_fixup(struct kmem_cache *s)
int node;
list_add(&s->list, &slab_caches);
@@ -71138,7 +70764,7 @@ index ed3334d..1739c9b 100644
for_each_node_state(node, N_NORMAL_MEMORY) {
struct kmem_cache_node *n = get_node(s, node);
-@@ -3744,17 +3794,17 @@ void __init kmem_cache_init(void)
+@@ -3749,17 +3794,17 @@ void __init kmem_cache_init(void)
/* Caches that are not of the two-to-the-power-of size */
if (KMALLOC_MIN_SIZE <= 32) {
@@ -71159,7 +70785,7 @@ index ed3334d..1739c9b 100644
caches++;
}
-@@ -3822,7 +3872,7 @@ static int slab_unmergeable(struct kmem_cache *s)
+@@ -3827,7 +3872,7 @@ static int slab_unmergeable(struct kmem_cache *s)
/*
* We may have set a slab to be unmergeable during bootstrap.
*/
@@ -71168,7 +70794,7 @@ index ed3334d..1739c9b 100644
return 1;
return 0;
-@@ -3881,7 +3931,7 @@ struct kmem_cache *kmem_cache_create(const char *name, size_t size,
+@@ -3886,7 +3931,7 @@ struct kmem_cache *kmem_cache_create(const char *name, size_t size,
down_write(&slub_lock);
s = find_mergeable(size, align, flags, name, ctor);
if (s) {
@@ -71177,7 +70803,7 @@ index ed3334d..1739c9b 100644
/*
* Adjust the object sizes so that we clear
* the complete object on kzalloc.
-@@ -3890,7 +3940,7 @@ struct kmem_cache *kmem_cache_create(const char *name, size_t size,
+@@ -3895,7 +3940,7 @@ struct kmem_cache *kmem_cache_create(const char *name, size_t size,
s->inuse = max_t(int, s->inuse, ALIGN(size, sizeof(void *)));
if (sysfs_slab_alias(s, name)) {
@@ -71186,7 +70812,7 @@ index ed3334d..1739c9b 100644
goto err;
}
up_write(&slub_lock);
-@@ -4018,7 +4068,7 @@ void *__kmalloc_node_track_caller(size_t size, gfp_t gfpflags,
+@@ -4023,7 +4068,7 @@ void *__kmalloc_node_track_caller(size_t size, gfp_t gfpflags,
}
#endif
@@ -71195,7 +70821,7 @@ index ed3334d..1739c9b 100644
static int count_inuse(struct page *page)
{
return page->inuse;
-@@ -4405,12 +4455,12 @@ static void resiliency_test(void)
+@@ -4410,12 +4455,12 @@ static void resiliency_test(void)
validate_slab_cache(kmalloc_caches[9]);
}
#else
@@ -71210,7 +70836,7 @@ index ed3334d..1739c9b 100644
enum slab_stat_type {
SL_ALL, /* All slabs */
SL_PARTIAL, /* Only partially allocated slabs */
-@@ -4651,7 +4701,7 @@ SLAB_ATTR_RO(ctor);
+@@ -4656,7 +4701,7 @@ SLAB_ATTR_RO(ctor);
static ssize_t aliases_show(struct kmem_cache *s, char *buf)
{
@@ -71219,7 +70845,7 @@ index ed3334d..1739c9b 100644
}
SLAB_ATTR_RO(aliases);
-@@ -5218,6 +5268,7 @@ static char *create_unique_id(struct kmem_cache *s)
+@@ -5223,6 +5268,7 @@ static char *create_unique_id(struct kmem_cache *s)
return name;
}
@@ -71227,7 +70853,7 @@ index ed3334d..1739c9b 100644
static int sysfs_slab_add(struct kmem_cache *s)
{
int err;
-@@ -5280,6 +5331,7 @@ static void sysfs_slab_remove(struct kmem_cache *s)
+@@ -5285,6 +5331,7 @@ static void sysfs_slab_remove(struct kmem_cache *s)
kobject_del(&s->kobj);
kobject_put(&s->kobj);
}
@@ -71235,7 +70861,7 @@ index ed3334d..1739c9b 100644
/*
* Need to buffer aliases during bootup until sysfs becomes
-@@ -5293,6 +5345,7 @@ struct saved_alias {
+@@ -5298,6 +5345,7 @@ struct saved_alias {
static struct saved_alias *alias_list;
@@ -71243,7 +70869,7 @@ index ed3334d..1739c9b 100644
static int sysfs_slab_alias(struct kmem_cache *s, const char *name)
{
struct saved_alias *al;
-@@ -5315,6 +5368,7 @@ static int sysfs_slab_alias(struct kmem_cache *s, const char *name)
+@@ -5320,6 +5368,7 @@ static int sysfs_slab_alias(struct kmem_cache *s, const char *name)
alias_list = al;
return 0;
}
@@ -73656,7 +73282,7 @@ index 1e733e9..3d73c9f 100644
return res;
}
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
-index ea10a51..9a4f0cc 100644
+index 73495f1..ad51356 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -27,6 +27,7 @@
@@ -73667,7 +73293,7 @@ index ea10a51..9a4f0cc 100644
#include "key.h"
#include "sta_info.h"
-@@ -761,7 +762,7 @@ struct ieee80211_local {
+@@ -764,7 +765,7 @@ struct ieee80211_local {
/* also used to protect ampdu_ac_queue and amdpu_ac_stop_refcnt */
spinlock_t queue_stop_reason_lock;
@@ -73735,10 +73361,10 @@ index 30d7355..e260095 100644
napi_disable(&local->napi);
ieee80211_clear_tx_pending(local);
diff --git a/net/mac80211/main.c b/net/mac80211/main.c
-index cae4435..76e3372 100644
+index a7536fd..4039cc0 100644
--- a/net/mac80211/main.c
+++ b/net/mac80211/main.c
-@@ -209,7 +209,7 @@ int ieee80211_hw_config(struct ieee80211_local *local, u32 changed)
+@@ -163,7 +163,7 @@ int ieee80211_hw_config(struct ieee80211_local *local, u32 changed)
local->hw.conf.power_level = power;
}
@@ -76460,7 +76086,7 @@ index 3ccf7ac..d73ad64 100644
};
extern struct ima_h_table ima_htable;
diff --git a/security/integrity/ima/ima_api.c b/security/integrity/ima/ima_api.c
-index 0d50df0..e94dd2a 100644
+index 88a2788..581ab92 100644
--- a/security/integrity/ima/ima_api.c
+++ b/security/integrity/ima/ima_api.c
@@ -75,7 +75,7 @@ void ima_add_violation(struct inode *inode, const unsigned char *filename,
@@ -76511,10 +76137,10 @@ index e1aa2b4..52027bf 100644
}
diff --git a/security/integrity/ima/ima_queue.c b/security/integrity/ima/ima_queue.c
-index 8e28f04..d5951b1 100644
+index 55a6271..ad829c3 100644
--- a/security/integrity/ima/ima_queue.c
+++ b/security/integrity/ima/ima_queue.c
-@@ -79,7 +79,7 @@ static int ima_add_digest_entry(struct ima_template_entry *entry)
+@@ -81,7 +81,7 @@ static int ima_add_digest_entry(struct ima_template_entry *entry)
INIT_LIST_HEAD(&qe->later);
list_add_tail_rcu(&qe->later, &ima_measurements);
diff --git a/main/linux-grsec/kernelconfig.x86 b/main/linux-grsec/kernelconfig.x86
index 9711293865..9ba8e66787 100644
--- a/main/linux-grsec/kernelconfig.x86
+++ b/main/linux-grsec/kernelconfig.x86
@@ -1,6 +1,6 @@
#
# Automatically generated file; DO NOT EDIT.
-# Linux/i386 3.2.1 Kernel Configuration
+# Linux/i386 3.2.2 Kernel Configuration
#
# CONFIG_64BIT is not set
CONFIG_X86_32=y
@@ -5171,6 +5171,7 @@ CONFIG_GRKERNSEC_PROC_IPADDR=y
#
# CONFIG_GRKERNSEC_DMESG is not set
CONFIG_GRKERNSEC_HARDEN_PTRACE=y
+CONFIG_GRKERNSEC_PTRACE_READEXEC=y
CONFIG_GRKERNSEC_SETXID=y
# CONFIG_GRKERNSEC_TPE is not set
diff --git a/main/linux-grsec/kernelconfig.x86_64 b/main/linux-grsec/kernelconfig.x86_64
index 433702e715..5fe9f305b7 100644
--- a/main/linux-grsec/kernelconfig.x86_64
+++ b/main/linux-grsec/kernelconfig.x86_64
@@ -5144,6 +5144,7 @@ CONFIG_GRKERNSEC_PROC_IPADDR=y
#
# CONFIG_GRKERNSEC_DMESG is not set
CONFIG_GRKERNSEC_HARDEN_PTRACE=y
+CONFIG_GRKERNSEC_PTRACE_READEXEC=y
CONFIG_GRKERNSEC_SETXID=y
# CONFIG_GRKERNSEC_TPE is not set