mirror of
https://github.com/chromium/crashpad.git
synced 2024-12-29 08:39:44 +08:00
linux: Fix interpretation of device numbers in /proc/pid/maps
While the kernel formats device major and minor numbers as %02x:%02x, they are not restricted to 8 bits apiece. Crashpad was requiring that the hexadecimal representations be exactly two characters, rather than at least two characters. The proper way to reconstruct a dev_t from major and minor numbers in user space is to use makedev() from <sys/sysmacros.h>. MKDEV() from <linux/kdev_t.h> interfaces with an older (pre-Linux 2.6) format which actually did use 8-bit major and minor numbers. makedev() places the major number at bits 8-19, and splits the minor number into two groups at bits 0-7 and 20-31. This is the correct user space view of device numbers. (Note that this is distinct from the kernel’s view: the kernel uses MKDEV() from a distinct internal <linux/kdev_t.h> which places the minor number at bits 0-19 and the major number at bits 20-31.) Bionic for 32-bit platforms uses a 32-bit user space dev_t while a 64-bit version is used elsewhere, and a comment in Bionic’s <sys/types.h> calls this a “historical accident”. However, due to the kernel’s use of only 32 bits for device numbers, this accident does not have any ill effect. Bug: crashpad:30 Test: crashpad_util_test, crashpad_snapshot_test Change-Id: Ic343454393d7399f598f9eba169a9e5f5630e601 Reviewed-on: https://chromium-review.googlesource.com/733863 Reviewed-by: Joshua Peraza <jperaza@chromium.org>
This commit is contained in:
parent
2f4516f938
commit
aff8d906b6
@ -14,9 +14,9 @@
|
|||||||
|
|
||||||
#include "util/linux/memory_map.h"
|
#include "util/linux/memory_map.h"
|
||||||
|
|
||||||
#include <linux/kdev_t.h>
|
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
#include <sys/sysmacros.h>
|
||||||
|
|
||||||
#include "base/files/file_path.h"
|
#include "base/files/file_path.h"
|
||||||
#include "base/logging.h"
|
#include "base/logging.h"
|
||||||
@ -147,16 +147,25 @@ ParseResult ParseMapsLine(DelimitedFileReader* maps_file_reader,
|
|||||||
return ParseResult::kError;
|
return ParseResult::kError;
|
||||||
}
|
}
|
||||||
|
|
||||||
int major, minor;
|
uint32_t major;
|
||||||
if (maps_file_reader->GetDelim(' ', &field) !=
|
if (maps_file_reader->GetDelim(':', &field) !=
|
||||||
DelimitedFileReader::Result::kSuccess ||
|
DelimitedFileReader::Result::kSuccess ||
|
||||||
(field.pop_back(), field.size() != 5) ||
|
(field.pop_back(), field.size()) < 2 ||
|
||||||
!HexStringToNumber(field.substr(0, 2), &major) ||
|
!HexStringToNumber(field, &major)) {
|
||||||
!HexStringToNumber(field.substr(3, 2), &minor)) {
|
|
||||||
LOG(ERROR) << "format error";
|
LOG(ERROR) << "format error";
|
||||||
return ParseResult::kError;
|
return ParseResult::kError;
|
||||||
}
|
}
|
||||||
mapping.device = MKDEV(major, minor);
|
|
||||||
|
uint32_t minor;
|
||||||
|
if (maps_file_reader->GetDelim(' ', &field) !=
|
||||||
|
DelimitedFileReader::Result::kSuccess ||
|
||||||
|
(field.pop_back(), field.size()) < 2 ||
|
||||||
|
!HexStringToNumber(field, &minor)) {
|
||||||
|
LOG(ERROR) << "format error";
|
||||||
|
return ParseResult::kError;
|
||||||
|
}
|
||||||
|
|
||||||
|
mapping.device = makedev(major, minor);
|
||||||
|
|
||||||
if (maps_file_reader->GetDelim(' ', &field) !=
|
if (maps_file_reader->GetDelim(' ', &field) !=
|
||||||
DelimitedFileReader::Result::kSuccess ||
|
DelimitedFileReader::Result::kSuccess ||
|
||||||
|
Loading…
x
Reference in New Issue
Block a user