* [PATCH 0/5] leaking_addresses: support 5 page table level
@ 2017-12-07 4:32 Tobin C. Harding
2017-12-07 4:32 ` [PATCH 1/5] leaking_addresses: remove command examples Tobin C. Harding
` (4 more replies)
0 siblings, 5 replies; 7+ messages in thread
From: Tobin C. Harding @ 2017-12-07 4:32 UTC (permalink / raw)
To: me, kaiwan.billimoria
Cc: Kirill A. Shutemov, Alexander Kapshuk, LKML, kernel-hardening
This set adds support for 5 page table levels on x86_64.
Patch 1 and 2 are clean up.
Patch 3 adds checking vsyscall memory region instead of just first and
last address.
Patch 4 adds support for locating and parsing the current kernel config
file. It feels like this may be re-inventing the wheel (also the
implementation is not as thorough as scripts/extract-ikconfig?) Much of
the code for this has been posted on LKML a few times now by Kaiwan
Billimoria. As such, it uses the new Co-Developed-by tag.
Patch 5 adds the 5 page table levels stuff. It is trivial once we have a
value from CONFIG_PGTABLE_LEVELS. Just set the regular expression
accordingly.
Perl tips, and code style tips in general, most appreciated.
As usual, any kernel development protocol tips also most
appreciated. Both Kaiwan and myself are pretty new around here, feel
free to give us a kick if we need it.
thanks,
Tobin.
Tobin C. Harding (5):
leaking_addresses: remove command examples
leaking_addresses: indent dependant options
leaking_addresses: add range check for vsyscall memory
leaking_addresses: add support for kernel config file
leaking_addresses: add support for 5 page table levels
scripts/leaking_addresses.pl | 169 +++++++++++++++++++++++++++++++++++--------
1 file changed, 137 insertions(+), 32 deletions(-)
--
2.7.4
^ permalink raw reply [flat|nested] 7+ messages in thread
* [PATCH 1/5] leaking_addresses: remove command examples
2017-12-07 4:32 [PATCH 0/5] leaking_addresses: support 5 page table level Tobin C. Harding
@ 2017-12-07 4:32 ` Tobin C. Harding
2017-12-07 4:32 ` [PATCH 2/5] leaking_addresses: indent dependant options Tobin C. Harding
` (3 subsequent siblings)
4 siblings, 0 replies; 7+ messages in thread
From: Tobin C. Harding @ 2017-12-07 4:32 UTC (permalink / raw)
To: me, kaiwan.billimoria
Cc: Kirill A. Shutemov, Alexander Kapshuk, LKML, kernel-hardening
Currently help output includes command examples. These were cute when we
first started development of this script but are unnecessary.
Remove command examples.
Signed-off-by: Tobin C. Harding <me@tobin.cc>
---
scripts/leaking_addresses.pl | 11 -----------
1 file changed, 11 deletions(-)
diff --git a/scripts/leaking_addresses.pl b/scripts/leaking_addresses.pl
index 1c5637db82a5..2c5da2296e94 100755
--- a/scripts/leaking_addresses.pl
+++ b/scripts/leaking_addresses.pl
@@ -102,17 +102,6 @@ Options:
-d, --debug Display debugging output.
-h, --help, --version Display this help and exit.
-Examples:
-
- # Scan kernel and dump raw results.
- $0
-
- # Scan kernel and save results to file.
- $0 --output-raw scan.out
-
- # View summary report.
- $0 --input-raw scan.out --squash-by-filename
-
Scans the running (64 bit) kernel for potential leaking addresses.
EOM
--
2.7.4
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 2/5] leaking_addresses: indent dependant options
2017-12-07 4:32 [PATCH 0/5] leaking_addresses: support 5 page table level Tobin C. Harding
2017-12-07 4:32 ` [PATCH 1/5] leaking_addresses: remove command examples Tobin C. Harding
@ 2017-12-07 4:32 ` Tobin C. Harding
2017-12-07 4:32 ` [PATCH 3/5] leaking_addresses: add range check for vsyscall memory Tobin C. Harding
` (2 subsequent siblings)
4 siblings, 0 replies; 7+ messages in thread
From: Tobin C. Harding @ 2017-12-07 4:32 UTC (permalink / raw)
To: me, kaiwan.billimoria
Cc: Kirill A. Shutemov, Alexander Kapshuk, LKML, kernel-hardening
A number of the command line options to script are dependant on the
option --input-raw being set. If we indent these options it makes
explicit this dependency.
Indent options dependant on --raw-input.
Signed-off-by: Tobin C. Harding <me@tobin.cc>
---
scripts/leaking_addresses.pl | 16 ++++++++--------
1 file changed, 8 insertions(+), 8 deletions(-)
diff --git a/scripts/leaking_addresses.pl b/scripts/leaking_addresses.pl
index 2c5da2296e94..066c609b1adb 100755
--- a/scripts/leaking_addresses.pl
+++ b/scripts/leaking_addresses.pl
@@ -93,14 +93,14 @@ Version: $V
Options:
- -o, --output-raw=<file> Save results for future processing.
- -i, --input-raw=<file> Read results from file instead of scanning.
- --raw Show raw results (default).
- --suppress-dmesg Do not show dmesg results.
- --squash-by-path Show one result per unique path.
- --squash-by-filename Show one result per unique filename.
- -d, --debug Display debugging output.
- -h, --help, --version Display this help and exit.
+ -o, --output-raw=<file> Save results for future processing.
+ -i, --input-raw=<file> Read results from file instead of scanning.
+ --raw Show raw results (default).
+ --suppress-dmesg Do not show dmesg results.
+ --squash-by-path Show one result per unique path.
+ --squash-by-filename Show one result per unique filename.
+ -d, --debug Display debugging output.
+ -h, --help, --versionq Display this help and exit.
Scans the running (64 bit) kernel for potential leaking addresses.
--
2.7.4
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 3/5] leaking_addresses: add range check for vsyscall memory
2017-12-07 4:32 [PATCH 0/5] leaking_addresses: support 5 page table level Tobin C. Harding
2017-12-07 4:32 ` [PATCH 1/5] leaking_addresses: remove command examples Tobin C. Harding
2017-12-07 4:32 ` [PATCH 2/5] leaking_addresses: indent dependant options Tobin C. Harding
@ 2017-12-07 4:32 ` Tobin C. Harding
2017-12-07 4:32 ` [PATCH 4/5] leaking_addresses: add support for kernel config file Tobin C. Harding
2017-12-07 4:32 ` [PATCH 5/5] leaking_addresses: add support for 5 page table levels Tobin C. Harding
4 siblings, 0 replies; 7+ messages in thread
From: Tobin C. Harding @ 2017-12-07 4:32 UTC (permalink / raw)
To: me, kaiwan.billimoria
Cc: Kirill A. Shutemov, Alexander Kapshuk, LKML, kernel-hardening
Currently script checks only first and last address in the vsyscall
memory range. We can do better than this.
When checking for false positives against $match, convert $match to
a hexadecimal value then check if it lies within the range of vsyscall
addresses.
Signed-off-by: Tobin C. Harding <me@tobin.cc>
---
scripts/leaking_addresses.pl | 20 ++++++++++++++------
1 file changed, 14 insertions(+), 6 deletions(-)
diff --git a/scripts/leaking_addresses.pl b/scripts/leaking_addresses.pl
index 066c609b1adb..cb69ccd4153a 100755
--- a/scripts/leaking_addresses.pl
+++ b/scripts/leaking_addresses.pl
@@ -20,6 +20,7 @@ use Cwd 'abs_path';
use Term::ANSIColor qw(:constants);
use Getopt::Long qw(:config no_auto_abbrev);
use Config;
+use bigint qw/hex/;
my $P = $0;
my $V = '0.01';
@@ -196,17 +197,24 @@ sub is_false_positive
return 1;
}
- if (is_x86_64()) {
- # vsyscall memory region, we should probably check against a range here.
- if ($match =~ '\bf{10}600000\b' or
- $match =~ '\bf{10}601000\b') {
- return 1;
- }
+ if (is_x86_64() and is_in_vsyscall_memory_region($match)) {
+ return 1;
}
return 0;
}
+sub is_in_vsyscall_memory_region
+{
+ my ($match) = @_;
+
+ my $hex = hex($match);
+ my $region_min = hex("0xffffffffff600000");
+ my $region_max = hex("0xffffffffff601000");
+
+ return ($hex >= $region_min and $hex <= $region_max);
+}
+
# True if argument potentially contains a kernel address.
sub may_leak_address
{
--
2.7.4
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 4/5] leaking_addresses: add support for kernel config file
2017-12-07 4:32 [PATCH 0/5] leaking_addresses: support 5 page table level Tobin C. Harding
` (2 preceding siblings ...)
2017-12-07 4:32 ` [PATCH 3/5] leaking_addresses: add range check for vsyscall memory Tobin C. Harding
@ 2017-12-07 4:32 ` Tobin C. Harding
2017-12-08 1:55 ` Kaiwan N Billimoria
2017-12-07 4:32 ` [PATCH 5/5] leaking_addresses: add support for 5 page table levels Tobin C. Harding
4 siblings, 1 reply; 7+ messages in thread
From: Tobin C. Harding @ 2017-12-07 4:32 UTC (permalink / raw)
To: me, kaiwan.billimoria
Cc: Kirill A. Shutemov, Alexander Kapshuk, LKML, kernel-hardening
Features that rely on the ability to get kernel configuration options
are ready to be implemented in script. In preparation for this we can
add support for kernel config options as a separate patch to ease
review.
Add support for locating and parsing kernel configuration file.
Signed-off-by: Tobin C. Harding <me@tobin.cc>
Co-Developed-by: Kaiwan N Billimoria <kaiwan.billimoria@gmail.com>
---
get_kernel_config_option() is not super clean, any improvements most welcome.
Kaiwan,
This needs your Signed-off-by tag if you want me to apply it with
the Co-Developed-tag
thanks,
Tobin.
scripts/leaking_addresses.pl | 64 +++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 63 insertions(+), 1 deletion(-)
diff --git a/scripts/leaking_addresses.pl b/scripts/leaking_addresses.pl
index cb69ccd4153a..892bfe9e01fe 100755
--- a/scripts/leaking_addresses.pl
+++ b/scripts/leaking_addresses.pl
@@ -42,10 +42,10 @@ my $debug = 0;
my $raw = 0;
my $output_raw = ""; # Write raw results to file.
my $input_raw = ""; # Read raw results from file instead of scanning.
-
my $suppress_dmesg = 0; # Don't show dmesg in output.
my $squash_by_path = 0; # Summary report grouped by absolute path.
my $squash_by_filename = 0; # Summary report grouped by filename.
+my $kernel_config_file = ""; # Kernel configuration file.
# Do not parse these files (absolute path).
my @skip_parse_files_abs = ('/proc/kmsg',
@@ -100,6 +100,7 @@ Options:
--suppress-dmesg Do not show dmesg results.
--squash-by-path Show one result per unique path.
--squash-by-filename Show one result per unique filename.
+ --kernel-config-file=<file> Kernel configuration file (e.g /boot/config)
-d, --debug Display debugging output.
-h, --help, --versionq Display this help and exit.
@@ -119,6 +120,7 @@ GetOptions(
'squash-by-path' => \$squash_by_path,
'squash-by-filename' => \$squash_by_filename,
'raw' => \$raw,
+ 'kernel-config-file=s' => \$kernel_config_file,
) or help(1);
help(0) if ($help);
@@ -188,6 +190,66 @@ sub is_ppc64
return 0;
}
+# gets config option value from kernel config file
+sub get_kernel_config_option
+{
+ my ($option) = @_;
+ my $value = "";
+ my $tmp_file = "";
+ my @config_files;
+
+ # Allow --kernel-config-file to override.
+ if ($kernel_config_file ne "") {
+ @config_files = ($kernel_config_file);
+ } elsif (-R "/proc/config.gz") {
+ my $tmp_file = "/tmp/tmpkconf";
+
+ if (system("gunzip < /proc/config.gz > $tmp_file")) {
+ dprint "$0: system(gunzip < /proc/config.gz) failed\n";
+ } else {
+ @config_files = ($tmp_file);
+ }
+
+ } else {
+ my $file = '/boot/config-' . `uname -r`;
+ @config_files = ($file, '/boot/config');
+ }
+
+ foreach my $file (@config_files) {
+# chomp $config_file;
+ $value = option_from_file($option, $file);
+ if ($value ne "") {
+ last;
+ }
+ }
+
+ if ($tmp_file ne "") {
+ system("rm -f $tmp_file");
+ }
+
+ return $value;
+}
+
+# Parses $file and returns kernel configuration option value.
+sub option_from_file
+{
+ my ($option, $file) = @_;
+ my $str = "";
+ my $val = "";
+
+ open(my $fh, "<", $file) or return "";
+ while (my $line = <$fh> ) {
+ if ($line =~ /^$option/) {
+ ($str, $val) = split /=/, $line;
+ chomp($val);
+ last;
+ }
+ }
+
+ close $fh;
+ return $val;
+}
+
sub is_false_positive
{
my ($match) = @_;
--
2.7.4
^ permalink raw reply related [flat|nested] 7+ messages in thread
* [PATCH 5/5] leaking_addresses: add support for 5 page table levels
2017-12-07 4:32 [PATCH 0/5] leaking_addresses: support 5 page table level Tobin C. Harding
` (3 preceding siblings ...)
2017-12-07 4:32 ` [PATCH 4/5] leaking_addresses: add support for kernel config file Tobin C. Harding
@ 2017-12-07 4:32 ` Tobin C. Harding
4 siblings, 0 replies; 7+ messages in thread
From: Tobin C. Harding @ 2017-12-07 4:32 UTC (permalink / raw)
To: me, kaiwan.billimoria
Cc: Kirill A. Shutemov, Alexander Kapshuk, LKML, kernel-hardening
Currently script only supports 4 page table levels because of the way
the kernel address regular expression is crafted. We can do better than
this. Using previously added support for kernel configuration options we
can get the number of page table levels defined by
CONFIG_PGTABLE_LEVELS. Using this value a correct regular expression can
be crafted. This only supports 5 page tables on x86_64.
Add support for 5 page table levels on x86_64.
Signed-off-by: Tobin C. Harding <me@tobin.cc>
---
scripts/leaking_addresses.pl | 60 ++++++++++++++++++++++++++++++++++++++------
1 file changed, 53 insertions(+), 7 deletions(-)
diff --git a/scripts/leaking_addresses.pl b/scripts/leaking_addresses.pl
index 892bfe9e01fe..82be5f18ea5f 100755
--- a/scripts/leaking_addresses.pl
+++ b/scripts/leaking_addresses.pl
@@ -21,6 +21,7 @@ use Term::ANSIColor qw(:constants);
use Getopt::Long qw(:config no_auto_abbrev);
use Config;
use bigint qw/hex/;
+use feature 'state';
my $P = $0;
my $V = '0.01';
@@ -39,12 +40,14 @@ my @SUPPORTED_ARCHITECTURES = ('x86_64', 'ppc64');
# Command line options.
my $help = 0;
my $debug = 0;
+
my $raw = 0;
my $output_raw = ""; # Write raw results to file.
my $input_raw = ""; # Read raw results from file instead of scanning.
my $suppress_dmesg = 0; # Don't show dmesg in output.
my $squash_by_path = 0; # Summary report grouped by absolute path.
my $squash_by_filename = 0; # Summary report grouped by filename.
+
my $kernel_config_file = ""; # Kernel configuration file.
# Do not parse these files (absolute path).
@@ -212,11 +215,13 @@ sub get_kernel_config_option
} else {
my $file = '/boot/config-' . `uname -r`;
+ chomp $file;
@config_files = ($file, '/boot/config');
}
foreach my $file (@config_files) {
-# chomp $config_file;
+ printf("file: %s\n", $file);
+
$value = option_from_file($option, $file);
if ($value ne "") {
last;
@@ -295,12 +300,8 @@ sub may_leak_address
return 0;
}
- # One of these is guaranteed to be true.
- if (is_x86_64()) {
- $address_re = '\b(0x)?ffff[[:xdigit:]]{12}\b';
- } elsif (is_ppc64()) {
- $address_re = '\b(0x)?[89abcdef]00[[:xdigit:]]{13}\b';
- }
+ $address_re = get_address_re();
+ dprint("Kernel address regular expression: %s\n", $address_re);
while (/($address_re)/g) {
if (!is_false_positive($1)) {
@@ -311,6 +312,51 @@ sub may_leak_address
return 0;
}
+sub get_address_re
+{
+ my $re;
+
+ if (is_x86_64()) {
+ $re = get_x86_64_re();
+ } elsif (is_ppc64()) {
+ $re = '\b(0x)?[89abcdef]00[[:xdigit:]]{13}\b';
+ }
+
+ if ($re eq "") {
+ print STDERR "$0: failed to build kernel address regular expression\n";
+ }
+
+ return $re;
+}
+
+sub get_x86_64_re
+{
+ state $ptl = get_page_table_levels();
+ my $re;
+
+ if ($ptl == 5) {
+ $re = '\b(0x)?ff[[:xdigit:]]{14}\b';
+ } else {
+ $re = '\b(0x)?ffff[[:xdigit:]]{12}\b';
+ }
+
+ return $re;
+}
+
+sub get_page_table_levels
+{
+ my $ptl = "";
+ my $default_ptl = "4";
+
+ $ptl = get_kernel_config_option('CONFIG_PGTABLE_LEVELS');
+ if ($ptl eq "") {
+ $ptl = $default_ptl;
+ printf(STDERR "$0: defaulting to %s page table levels\n", $default_ptl);
+ }
+
+ return $ptl;
+}
+
sub parse_dmesg
{
open my $cmd, '-|', 'dmesg';
--
2.7.4
^ permalink raw reply related [flat|nested] 7+ messages in thread
* Re: [PATCH 4/5] leaking_addresses: add support for kernel config file
2017-12-07 4:32 ` [PATCH 4/5] leaking_addresses: add support for kernel config file Tobin C. Harding
@ 2017-12-08 1:55 ` Kaiwan N Billimoria
0 siblings, 0 replies; 7+ messages in thread
From: Kaiwan N Billimoria @ 2017-12-08 1:55 UTC (permalink / raw)
To: Tobin C. Harding
Cc: Kirill A. Shutemov, Alexander Kapshuk, LKML, kernel-hardening
On Thu, Dec 7, 2017 at 10:02 AM, Tobin C. Harding <me@tobin.cc> wrote:
> Features that rely on the ability to get kernel configuration options
> are ready to be implemented in script. In preparation for this we can
> add support for kernel config options as a separate patch to ease
> review.
>
> Add support for locating and parsing kernel configuration file.
>
> Signed-off-by: Tobin C. Harding <me@tobin.cc>
> Co-Developed-by: Kaiwan N Billimoria <kaiwan.billimoria@gmail.com>
> ---
>
> get_kernel_config_option() is not super clean, any improvements most welcome.
>
> Kaiwan,
>
> This needs your Signed-off-by tag if you want me to apply it with
> the Co-Developed-tag
>
> thanks,
> Tobin.
>
Adding my signed-off tag..
Signed-off-by: Kaiwan N Billimoria <kaiwan.billimoria@gmail.com>
> scripts/leaking_addresses.pl | 64 +++++++++++++++++++++++++++++++++++++++++++-
> 1 file changed, 63 insertions(+), 1 deletion(-)
>
> diff --git a/scripts/leaking_addresses.pl b/scripts/leaking_addresses.pl
> index cb69ccd4153a..892bfe9e01fe 100755
> --- a/scripts/leaking_addresses.pl
> +++ b/scripts/leaking_addresses.pl
> @@ -42,10 +42,10 @@ my $debug = 0;
> my $raw = 0;
> my $output_raw = ""; # Write raw results to file.
> my $input_raw = ""; # Read raw results from file instead of scanning.
> -
> my $suppress_dmesg = 0; # Don't show dmesg in output.
> my $squash_by_path = 0; # Summary report grouped by absolute path.
> my $squash_by_filename = 0; # Summary report grouped by filename.
> +my $kernel_config_file = ""; # Kernel configuration file.
>
> # Do not parse these files (absolute path).
> my @skip_parse_files_abs = ('/proc/kmsg',
> @@ -100,6 +100,7 @@ Options:
> --suppress-dmesg Do not show dmesg results.
> --squash-by-path Show one result per unique path.
> --squash-by-filename Show one result per unique filename.
> + --kernel-config-file=<file> Kernel configuration file (e.g /boot/config)
> -d, --debug Display debugging output.
> -h, --help, --versionq Display this help and exit.
>
> @@ -119,6 +120,7 @@ GetOptions(
> 'squash-by-path' => \$squash_by_path,
> 'squash-by-filename' => \$squash_by_filename,
> 'raw' => \$raw,
> + 'kernel-config-file=s' => \$kernel_config_file,
> ) or help(1);
>
> help(0) if ($help);
> @@ -188,6 +190,66 @@ sub is_ppc64
> return 0;
> }
>
> +# gets config option value from kernel config file
> +sub get_kernel_config_option
> +{
> + my ($option) = @_;
> + my $value = "";
> + my $tmp_file = "";
> + my @config_files;
> +
> + # Allow --kernel-config-file to override.
> + if ($kernel_config_file ne "") {
> + @config_files = ($kernel_config_file);
> + } elsif (-R "/proc/config.gz") {
> + my $tmp_file = "/tmp/tmpkconf";
> +
> + if (system("gunzip < /proc/config.gz > $tmp_file")) {
> + dprint "$0: system(gunzip < /proc/config.gz) failed\n";
> + } else {
> + @config_files = ($tmp_file);
> + }
> +
> + } else {
> + my $file = '/boot/config-' . `uname -r`;
> + @config_files = ($file, '/boot/config');
> + }
> +
> + foreach my $file (@config_files) {
> +# chomp $config_file;
> + $value = option_from_file($option, $file);
> + if ($value ne "") {
> + last;
> + }
> + }
> +
> + if ($tmp_file ne "") {
> + system("rm -f $tmp_file");
> + }
> +
> + return $value;
> +}
> +
> +# Parses $file and returns kernel configuration option value.
> +sub option_from_file
> +{
> + my ($option, $file) = @_;
> + my $str = "";
> + my $val = "";
> +
> + open(my $fh, "<", $file) or return "";
> + while (my $line = <$fh> ) {
> + if ($line =~ /^$option/) {
> + ($str, $val) = split /=/, $line;
> + chomp($val);
> + last;
> + }
> + }
> +
> + close $fh;
> + return $val;
> +}
> +
> sub is_false_positive
> {
> my ($match) = @_;
> --
> 2.7.4
>
^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2017-12-08 1:55 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-12-07 4:32 [PATCH 0/5] leaking_addresses: support 5 page table level Tobin C. Harding
2017-12-07 4:32 ` [PATCH 1/5] leaking_addresses: remove command examples Tobin C. Harding
2017-12-07 4:32 ` [PATCH 2/5] leaking_addresses: indent dependant options Tobin C. Harding
2017-12-07 4:32 ` [PATCH 3/5] leaking_addresses: add range check for vsyscall memory Tobin C. Harding
2017-12-07 4:32 ` [PATCH 4/5] leaking_addresses: add support for kernel config file Tobin C. Harding
2017-12-08 1:55 ` Kaiwan N Billimoria
2017-12-07 4:32 ` [PATCH 5/5] leaking_addresses: add support for 5 page table levels Tobin C. Harding
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).