pub use codespan::{
ByteIndex as BytePos, ByteOffset, ColumnIndex as Column, ColumnOffset, LineIndex as Line,
LineOffset,
};
#[derive(
Copy, Clone, Default, Eq, PartialEq, Debug, Hash, Ord, PartialOrd, Serialize, Deserialize,
)]
pub struct Location {
pub unit_id: usize, line: usize,
column: usize,
absolute: usize,
}
impl std::ops::Sub for Location {
type Output = Location;
fn sub(self, rhs: Location) -> Self::Output {
Location {
unit_id: self.unit_id,
line: self.line.saturating_sub(rhs.line),
column: self.column.saturating_sub(rhs.column),
absolute: self.absolute.saturating_sub(rhs.absolute),
}
}
}
#[derive(Copy, Clone, Default, Eq, PartialEq, Debug, Hash, Ord, PartialOrd)]
pub struct Span {
pub start: Location,
pub end: Location,
pub pp_start: Location,
pub pp_end: Location,
}
impl Span {
pub(crate) fn new(
start: Location,
end: Location,
pp_start: Location,
pp_end: Location,
) -> Self {
Self {
start,
end,
pp_start,
pp_end,
}
}
pub(crate) fn start(&self) -> Location {
self.start
}
pub(crate) fn end(&self) -> Location {
self.end
}
}
pub(crate) fn span(start: Location, end: Location, pp_start: Location, pp_end: Location) -> Span {
Span::new(start, end, pp_start, pp_end)
}
#[derive(Copy, Clone, Debug, Eq, PartialEq, Default)]
pub struct Spanned<T> {
pub span: Span,
pub value: T,
}
#[derive(
Copy, Clone, Default, Eq, PartialEq, Debug, Hash, Ord, PartialOrd, Serialize, Deserialize,
)]
pub struct Range(pub(crate) Location, pub(crate) Location);
impl Range {
pub(crate) fn expand_lines(&self, lines: usize) -> Self {
let mut new = *self;
new.0 = new.0.move_up_lines(lines);
new.1 = new.1.move_down_lines(lines);
new
}
#[must_use]
pub fn cu(self) -> usize {
self.0.unit_id
}
}
impl From<(Location, Location)> for Range {
fn from(locs: (Location, Location)) -> Self {
Self(locs.0, locs.1)
}
}
impl Location {
#[must_use]
pub fn new(line: usize, column: usize, absolute: usize, unit_id: usize) -> Self {
Self {
line,
column,
absolute,
unit_id,
}
}
#[must_use]
pub fn start_of_line(&self) -> Self {
let mut new = *self;
new.column = 0;
new
}
#[must_use]
pub fn absolute(&self) -> usize {
self.absolute
}
#[must_use]
pub fn line(&self) -> usize {
self.line
}
#[must_use]
pub fn column(&self) -> usize {
self.column
}
pub(crate) fn set_cu(&mut self, cu: usize) {
self.unit_id = cu;
}
#[must_use]
pub fn for_line_directive() -> Self {
Self {
line: 0,
column: 0,
absolute: 0,
unit_id: 0,
}
}
pub(crate) fn move_down_lines(&self, lines: usize) -> Self {
let mut new = *self;
new.line += lines;
new
}
pub(crate) fn move_up_lines(&self, lines: usize) -> Self {
let mut new = *self;
new.line = self.line.saturating_sub(lines);
new
}
pub(crate) fn shift(&mut self, ch: char) {
if ch == '\n' {
self.line += 1;
self.column = 1;
} else {
self.column += 1;
}
self.absolute += ch.len_utf8();
}
}