Fix for loop ctrlc not terminating (#5003)
This commit is contained in:
parent
a87f53072a
commit
2e3b74f1b2
|
@ -125,7 +125,7 @@ https://www.nushell.sh/book/thinking_in_nushell.html#parsing-and-evaluation-are-
|
||||||
.filter(|x| !x.is_nothing())
|
.filter(|x| !x.is_nothing())
|
||||||
.into_pipeline_data(ctrlc)),
|
.into_pipeline_data(ctrlc)),
|
||||||
Value::Range { val, .. } => Ok(val
|
Value::Range { val, .. } => Ok(val
|
||||||
.into_range_iter()?
|
.into_range_iter(ctrlc.clone())?
|
||||||
.enumerate()
|
.enumerate()
|
||||||
.map(move |(idx, x)| {
|
.map(move |(idx, x)| {
|
||||||
stack.with_env(&orig_env_vars, &orig_env_hidden);
|
stack.with_env(&orig_env_vars, &orig_env_hidden);
|
||||||
|
|
|
@ -71,7 +71,7 @@ impl Command for ParEach {
|
||||||
|
|
||||||
match input {
|
match input {
|
||||||
PipelineData::Value(Value::Range { val, .. }, ..) => Ok(val
|
PipelineData::Value(Value::Range { val, .. }, ..) => Ok(val
|
||||||
.into_range_iter()?
|
.into_range_iter(ctrlc.clone())?
|
||||||
.enumerate()
|
.enumerate()
|
||||||
.par_bridge()
|
.par_bridge()
|
||||||
.map(move |(idx, x)| {
|
.map(move |(idx, x)| {
|
||||||
|
|
|
@ -81,7 +81,7 @@ pub fn calculate(
|
||||||
}
|
}
|
||||||
PipelineData::Value(Value::Range { val, .. }, ..) => {
|
PipelineData::Value(Value::Range { val, .. }, ..) => {
|
||||||
let new_vals: Result<Vec<Value>, ShellError> = val
|
let new_vals: Result<Vec<Value>, ShellError> = val
|
||||||
.into_range_iter()?
|
.into_range_iter(None)?
|
||||||
.map(|val| mf(&[val], &name))
|
.map(|val| mf(&[val], &name))
|
||||||
.collect();
|
.collect();
|
||||||
|
|
||||||
|
|
|
@ -283,9 +283,10 @@ impl PipelineData {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PipelineData::Value(Value::Range { val, .. }, ..) => {
|
PipelineData::Value(Value::Range { val, .. }, ..) => Ok(val
|
||||||
Ok(val.into_range_iter()?.map(f).into_pipeline_data(ctrlc))
|
.into_range_iter(ctrlc.clone())?
|
||||||
}
|
.map(f)
|
||||||
|
.into_pipeline_data(ctrlc)),
|
||||||
PipelineData::Value(v, ..) => match f(v) {
|
PipelineData::Value(v, ..) => match f(v) {
|
||||||
Value::Error { error } => Err(error),
|
Value::Error { error } => Err(error),
|
||||||
v => Ok(v.into_pipeline_data()),
|
v => Ok(v.into_pipeline_data()),
|
||||||
|
@ -337,10 +338,12 @@ impl PipelineData {
|
||||||
.into_pipeline_data(ctrlc))
|
.into_pipeline_data(ctrlc))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
PipelineData::Value(Value::Range { val, .. }, ..) => match val.into_range_iter() {
|
PipelineData::Value(Value::Range { val, .. }, ..) => {
|
||||||
Ok(iter) => Ok(iter.flat_map(f).into_pipeline_data(ctrlc)),
|
match val.into_range_iter(ctrlc.clone()) {
|
||||||
Err(error) => Err(error),
|
Ok(iter) => Ok(iter.flat_map(f).into_pipeline_data(ctrlc)),
|
||||||
},
|
Err(error) => Err(error),
|
||||||
|
}
|
||||||
|
}
|
||||||
PipelineData::Value(v, ..) => Ok(f(v).into_iter().into_pipeline_data(ctrlc)),
|
PipelineData::Value(v, ..) => Ok(f(v).into_iter().into_pipeline_data(ctrlc)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -392,9 +395,10 @@ impl PipelineData {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
PipelineData::Value(Value::Range { val, .. }, ..) => {
|
PipelineData::Value(Value::Range { val, .. }, ..) => Ok(val
|
||||||
Ok(val.into_range_iter()?.filter(f).into_pipeline_data(ctrlc))
|
.into_range_iter(ctrlc.clone())?
|
||||||
}
|
.filter(f)
|
||||||
|
.into_pipeline_data(ctrlc)),
|
||||||
PipelineData::Value(v, ..) => {
|
PipelineData::Value(v, ..) => {
|
||||||
if f(&v) {
|
if f(&v) {
|
||||||
Ok(v.into_pipeline_data())
|
Ok(v.into_pipeline_data())
|
||||||
|
@ -425,7 +429,7 @@ impl IntoIterator for PipelineData {
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
PipelineData::Value(Value::Range { val, .. }, metadata) => {
|
PipelineData::Value(Value::Range { val, .. }, metadata) => {
|
||||||
match val.into_range_iter() {
|
match val.into_range_iter(None) {
|
||||||
Ok(iter) => PipelineIterator(PipelineData::ListStream(
|
Ok(iter) => PipelineIterator(PipelineData::ListStream(
|
||||||
ListStream {
|
ListStream {
|
||||||
stream: Box::new(iter),
|
stream: Box::new(iter),
|
||||||
|
|
|
@ -605,7 +605,7 @@ impl Value {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Value::Range { val, .. } => {
|
Value::Range { val, .. } => {
|
||||||
if let Some(item) = val.clone().into_range_iter()?.nth(*count) {
|
if let Some(item) = val.clone().into_range_iter(None)?.nth(*count) {
|
||||||
current = item.clone();
|
current = item.clone();
|
||||||
} else {
|
} else {
|
||||||
return Err(ShellError::AccessBeyondEndOfStream(*origin_span));
|
return Err(ShellError::AccessBeyondEndOfStream(*origin_span));
|
||||||
|
|
|
@ -1,5 +1,8 @@
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
use std::cmp::Ordering;
|
use std::{
|
||||||
|
cmp::Ordering,
|
||||||
|
sync::{atomic::AtomicBool, Arc},
|
||||||
|
};
|
||||||
|
|
||||||
/// A Range is an iterator over integers.
|
/// A Range is an iterator over integers.
|
||||||
use crate::{
|
use crate::{
|
||||||
|
@ -122,10 +125,13 @@ impl Range {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn into_range_iter(self) -> Result<RangeIterator, ShellError> {
|
pub fn into_range_iter(
|
||||||
|
self,
|
||||||
|
ctrlc: Option<Arc<AtomicBool>>,
|
||||||
|
) -> Result<RangeIterator, ShellError> {
|
||||||
let span = self.from.span()?;
|
let span = self.from.span()?;
|
||||||
|
|
||||||
Ok(RangeIterator::new(self, span))
|
Ok(RangeIterator::new(self, ctrlc, span))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -155,10 +161,11 @@ pub struct RangeIterator {
|
||||||
moves_up: bool,
|
moves_up: bool,
|
||||||
incr: Value,
|
incr: Value,
|
||||||
done: bool,
|
done: bool,
|
||||||
|
ctrlc: Option<Arc<AtomicBool>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl RangeIterator {
|
impl RangeIterator {
|
||||||
pub fn new(range: Range, span: Span) -> RangeIterator {
|
pub fn new(range: Range, ctrlc: Option<Arc<AtomicBool>>, span: Span) -> RangeIterator {
|
||||||
let moves_up = range.moves_up();
|
let moves_up = range.moves_up();
|
||||||
let is_end_inclusive = range.is_end_inclusive();
|
let is_end_inclusive = range.is_end_inclusive();
|
||||||
|
|
||||||
|
@ -183,6 +190,7 @@ impl RangeIterator {
|
||||||
is_end_inclusive,
|
is_end_inclusive,
|
||||||
done: false,
|
done: false,
|
||||||
incr: range.incr,
|
incr: range.incr,
|
||||||
|
ctrlc,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -194,6 +202,12 @@ impl Iterator for RangeIterator {
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if let Some(ctrlc) = &self.ctrlc {
|
||||||
|
if ctrlc.load(core::sync::atomic::Ordering::SeqCst) {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
let ordering = if matches!(self.end, Value::Nothing { .. }) {
|
let ordering = if matches!(self.end, Value::Nothing { .. }) {
|
||||||
Some(Ordering::Less)
|
Some(Ordering::Less)
|
||||||
} else {
|
} else {
|
||||||
|
|
Loading…
Reference in New Issue
Block a user