mirror of
https://github.com/simonask/libyaml-safer
synced 2024-11-26 05:10:20 +00:00
Remove ForceAdd/ForceMul
This commit is contained in:
parent
176c0edfdb
commit
e28400ee5f
4 changed files with 11 additions and 128 deletions
|
@ -4,7 +4,6 @@ use crate::api::OUTPUT_BUFFER_SIZE;
|
||||||
use crate::macros::{
|
use crate::macros::{
|
||||||
is_alpha, is_ascii, is_blank, is_blankz, is_bom, is_break, is_breakz, is_printable, is_space,
|
is_alpha, is_ascii, is_blank, is_blankz, is_bom, is_break, is_breakz, is_printable, is_space,
|
||||||
};
|
};
|
||||||
use crate::ops::ForceMul as _;
|
|
||||||
use crate::yaml::YamlEventData;
|
use crate::yaml::YamlEventData;
|
||||||
use crate::{
|
use crate::{
|
||||||
yaml_emitter_flush, yaml_emitter_t, yaml_event_t, yaml_scalar_style_t, yaml_tag_directive_t,
|
yaml_emitter_flush, yaml_emitter_t, yaml_event_t, yaml_scalar_style_t, yaml_tag_directive_t,
|
||||||
|
@ -287,7 +286,7 @@ fn yaml_emitter_emit_stream_start(
|
||||||
if emitter.best_indent < 2 || emitter.best_indent > 9 {
|
if emitter.best_indent < 2 || emitter.best_indent > 9 {
|
||||||
emitter.best_indent = 2;
|
emitter.best_indent = 2;
|
||||||
}
|
}
|
||||||
if emitter.best_width >= 0 && emitter.best_width <= emitter.best_indent.force_mul(2) {
|
if emitter.best_width >= 0 && emitter.best_width <= emitter.best_indent * 2 {
|
||||||
emitter.best_width = 80;
|
emitter.best_width = 80;
|
||||||
}
|
}
|
||||||
if emitter.best_width < 0 {
|
if emitter.best_width < 0 {
|
||||||
|
|
|
@ -44,7 +44,6 @@ mod dumper;
|
||||||
mod emitter;
|
mod emitter;
|
||||||
mod error;
|
mod error;
|
||||||
mod loader;
|
mod loader;
|
||||||
mod ops;
|
|
||||||
mod parser;
|
mod parser;
|
||||||
mod reader;
|
mod reader;
|
||||||
mod scanner;
|
mod scanner;
|
||||||
|
|
111
src/ops.rs
111
src/ops.rs
|
@ -1,111 +0,0 @@
|
||||||
pub(crate) trait ForceAdd: Sized {
|
|
||||||
fn force_add(self, rhs: Self) -> Self;
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceAdd for u8 {
|
|
||||||
fn force_add(self, rhs: Self) -> Self {
|
|
||||||
self.checked_add(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceAdd for i32 {
|
|
||||||
fn force_add(self, rhs: Self) -> Self {
|
|
||||||
self.checked_add(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceAdd for u32 {
|
|
||||||
fn force_add(self, rhs: Self) -> Self {
|
|
||||||
self.checked_add(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceAdd for u64 {
|
|
||||||
fn force_add(self, rhs: Self) -> Self {
|
|
||||||
self.checked_add(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceAdd for usize {
|
|
||||||
fn force_add(self, rhs: Self) -> Self {
|
|
||||||
self.checked_add(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub(crate) trait ForceMul: Sized {
|
|
||||||
fn force_mul(self, rhs: Self) -> Self;
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceMul for i32 {
|
|
||||||
fn force_mul(self, rhs: Self) -> Self {
|
|
||||||
self.checked_mul(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceMul for i64 {
|
|
||||||
fn force_mul(self, rhs: Self) -> Self {
|
|
||||||
self.checked_mul(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ForceMul for u64 {
|
|
||||||
fn force_mul(self, rhs: Self) -> Self {
|
|
||||||
self.checked_mul(rhs).unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub(crate) trait ForceInto {
|
|
||||||
fn force_into<U>(self) -> U
|
|
||||||
where
|
|
||||||
Self: TryInto<U>;
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<T> ForceInto for T {
|
|
||||||
fn force_into<U>(self) -> U
|
|
||||||
where
|
|
||||||
Self: TryInto<U>,
|
|
||||||
{
|
|
||||||
<Self as TryInto<U>>::try_into(self)
|
|
||||||
.ok()
|
|
||||||
.unwrap_or_else(die)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Deterministically abort on arithmetic overflow, instead of wrapping and
|
|
||||||
// continuing with invalid behavior.
|
|
||||||
//
|
|
||||||
// This is impossible or nearly impossible to hit as the arithmetic computations
|
|
||||||
// in libyaml are all related to either:
|
|
||||||
//
|
|
||||||
// - small integer processing (ascii, hex digits)
|
|
||||||
// - allocation sizing
|
|
||||||
//
|
|
||||||
// and the only allocations in libyaml are for fixed-sized objects and
|
|
||||||
// geometrically growing buffers with a growth factor of 2. So in order for an
|
|
||||||
// allocation computation to overflow usize, the previous allocation for that
|
|
||||||
// container must have been filled to a size of usize::MAX/2, which is an
|
|
||||||
// allocation that would have failed in the allocator. But we check for this to
|
|
||||||
// be pedantic and to find out if it ever does happen.
|
|
||||||
//
|
|
||||||
// No-std abort is implemented using a double panic. On most platforms the
|
|
||||||
// current mechanism for this is for core::intrinsics::abort to invoke an
|
|
||||||
// invalid instruction. On Unix, the process will probably terminate with a
|
|
||||||
// signal like SIGABRT, SIGILL, SIGTRAP, SIGSEGV or SIGBUS. The precise
|
|
||||||
// behaviour is not guaranteed and not stable, but is safe.
|
|
||||||
#[cold]
|
|
||||||
pub(crate) fn die<T>() -> T {
|
|
||||||
struct PanicAgain;
|
|
||||||
|
|
||||||
impl Drop for PanicAgain {
|
|
||||||
fn drop(&mut self) {
|
|
||||||
panic!("arithmetic overflow");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn do_die() -> ! {
|
|
||||||
let _panic_again = PanicAgain;
|
|
||||||
panic!("arithmetic overflow");
|
|
||||||
}
|
|
||||||
|
|
||||||
do_die();
|
|
||||||
}
|
|
|
@ -1,7 +1,6 @@
|
||||||
use alloc::string::String;
|
use alloc::string::String;
|
||||||
|
|
||||||
use crate::macros::{is_blankz, is_break, vecdeque_starts_with};
|
use crate::macros::{is_blankz, is_break, vecdeque_starts_with};
|
||||||
use crate::ops::{ForceAdd as _, ForceMul as _};
|
|
||||||
use crate::reader::yaml_parser_update_buffer;
|
use crate::reader::yaml_parser_update_buffer;
|
||||||
use crate::yaml::YamlTokenData;
|
use crate::yaml::YamlTokenData;
|
||||||
use crate::{
|
use crate::{
|
||||||
|
@ -109,7 +108,7 @@ pub fn yaml_parser_scan(parser: &mut yaml_parser_t) -> Result<yaml_token_t, Scan
|
||||||
}
|
}
|
||||||
if let Some(token) = parser.tokens.pop_front() {
|
if let Some(token) = parser.tokens.pop_front() {
|
||||||
parser.token_available = false;
|
parser.token_available = false;
|
||||||
parser.tokens_parsed = parser.tokens_parsed.force_add(1);
|
parser.tokens_parsed += 1;
|
||||||
if let YamlTokenData::StreamEnd = &token.data {
|
if let YamlTokenData::StreamEnd = &token.data {
|
||||||
parser.stream_end_produced = true;
|
parser.stream_end_produced = true;
|
||||||
}
|
}
|
||||||
|
@ -275,7 +274,7 @@ fn yaml_parser_stale_simple_keys(parser: &mut yaml_parser_t) -> Result<(), Scann
|
||||||
for simple_key in &mut parser.simple_keys {
|
for simple_key in &mut parser.simple_keys {
|
||||||
let mark = simple_key.mark;
|
let mark = simple_key.mark;
|
||||||
if simple_key.possible
|
if simple_key.possible
|
||||||
&& (mark.line < parser.mark.line || mark.index.force_add(1024_u64) < parser.mark.index)
|
&& (mark.line < parser.mark.line || mark.index + 1024 < parser.mark.index)
|
||||||
{
|
{
|
||||||
if simple_key.required {
|
if simple_key.required {
|
||||||
return yaml_parser_set_scanner_error(
|
return yaml_parser_set_scanner_error(
|
||||||
|
@ -298,7 +297,7 @@ fn yaml_parser_save_simple_key(parser: &mut yaml_parser_t) -> Result<(), Scanner
|
||||||
let simple_key = yaml_simple_key_t {
|
let simple_key = yaml_simple_key_t {
|
||||||
possible: true,
|
possible: true,
|
||||||
required,
|
required,
|
||||||
token_number: parser.tokens_parsed.force_add(parser.tokens.len()),
|
token_number: parser.tokens_parsed + parser.tokens.len(),
|
||||||
mark: parser.mark,
|
mark: parser.mark,
|
||||||
};
|
};
|
||||||
yaml_parser_remove_simple_key(parser)?;
|
yaml_parser_remove_simple_key(parser)?;
|
||||||
|
@ -425,7 +424,7 @@ fn yaml_parser_fetch_stream_start(parser: &mut yaml_parser_t) {
|
||||||
fn yaml_parser_fetch_stream_end(parser: &mut yaml_parser_t) -> Result<(), ScannerError> {
|
fn yaml_parser_fetch_stream_end(parser: &mut yaml_parser_t) -> Result<(), ScannerError> {
|
||||||
if parser.mark.column != 0_u64 {
|
if parser.mark.column != 0_u64 {
|
||||||
parser.mark.column = 0_u64;
|
parser.mark.column = 0_u64;
|
||||||
parser.mark.line = parser.mark.line.force_add(1);
|
parser.mark.line += 1;
|
||||||
}
|
}
|
||||||
yaml_parser_unroll_indent(parser, -1_i64);
|
yaml_parser_unroll_indent(parser, -1_i64);
|
||||||
yaml_parser_remove_simple_key(parser)?;
|
yaml_parser_remove_simple_key(parser)?;
|
||||||
|
@ -868,7 +867,7 @@ fn yaml_parser_scan_version_directive_number(
|
||||||
let mut length = 0;
|
let mut length = 0;
|
||||||
CACHE(parser, 1)?;
|
CACHE(parser, 1)?;
|
||||||
while IS_DIGIT!(parser.buffer) {
|
while IS_DIGIT!(parser.buffer) {
|
||||||
length = length.force_add(1);
|
length += 1;
|
||||||
if length > MAX_NUMBER_LENGTH {
|
if length > MAX_NUMBER_LENGTH {
|
||||||
return yaml_parser_set_scanner_error(
|
return yaml_parser_set_scanner_error(
|
||||||
parser,
|
parser,
|
||||||
|
@ -877,9 +876,7 @@ fn yaml_parser_scan_version_directive_number(
|
||||||
"found extremely long version number",
|
"found extremely long version number",
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
value = value
|
value = (value * 10) + AS_DIGIT!(parser.buffer) as i32;
|
||||||
.force_mul(10)
|
|
||||||
.force_add(AS_DIGIT!(parser.buffer) as i32);
|
|
||||||
SKIP(parser);
|
SKIP(parser);
|
||||||
CACHE(parser, 1)?;
|
CACHE(parser, 1)?;
|
||||||
}
|
}
|
||||||
|
@ -1149,7 +1146,7 @@ fn yaml_parser_scan_tag_uri(
|
||||||
} else {
|
} else {
|
||||||
READ_STRING(parser, &mut string);
|
READ_STRING(parser, &mut string);
|
||||||
}
|
}
|
||||||
length = length.force_add(1);
|
length += 1;
|
||||||
CACHE(parser, 1)?;
|
CACHE(parser, 1)?;
|
||||||
}
|
}
|
||||||
if length == 0 {
|
if length == 0 {
|
||||||
|
@ -1605,9 +1602,8 @@ fn yaml_parser_scan_flow_scalar(
|
||||||
"did not find expected hexdecimal number",
|
"did not find expected hexdecimal number",
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
value = (value << 4)
|
value = (value << 4) + AS_HEX_AT!(parser.buffer, k as usize);
|
||||||
.force_add(AS_HEX_AT!(parser.buffer, k as usize));
|
k += 1;
|
||||||
k = k.force_add(1);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if let Some(ch) = char::from_u32(value) {
|
if let Some(ch) = char::from_u32(value) {
|
||||||
|
@ -1624,7 +1620,7 @@ fn yaml_parser_scan_flow_scalar(
|
||||||
k = 0;
|
k = 0;
|
||||||
while k < code_length {
|
while k < code_length {
|
||||||
SKIP(parser);
|
SKIP(parser);
|
||||||
k = k.force_add(1);
|
k += 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
Loading…
Reference in a new issue