Byte ahd char literals
diff --git a/src/escape.rs b/src/escape.rs
index 8eccb4e..65c2615 100644
--- a/src/escape.rs
+++ b/src/escape.rs
@@ -50,6 +50,31 @@
IResult::Error
}
+pub fn cooked_char(input: &str) -> IResult<&str, char> {
+ let mut chars = input.char_indices();
+ let ch = match chars.next().map(|(_, ch)| ch) {
+ Some('\\') => {
+ match chars.next().map(|(_, ch)| ch) {
+ Some('x') => backslash_x(&mut chars),
+ Some('n') => Some('\n'),
+ Some('r') => Some('\r'),
+ Some('t') => Some('\t'),
+ Some('\\') => Some('\\'),
+ Some('0') => Some('\0'),
+ Some('u') => backslash_u(&mut chars),
+ Some('\'') => Some('\''),
+ Some('"') => Some('"'),
+ _ => None,
+ }
+ }
+ ch => ch,
+ };
+ match ch {
+ Some(ch) => IResult::Done(chars.as_str(), ch),
+ None => IResult::Error,
+ }
+}
+
pub fn raw_string(input: &str) -> IResult<&str, (String, usize)> {
let mut chars = input.char_indices();
let mut n = 0;
diff --git a/src/lit.rs b/src/lit.rs
index b143a9d..c1a2876 100644
--- a/src/lit.rs
+++ b/src/lit.rs
@@ -54,7 +54,7 @@
#[cfg(feature = "parsing")]
pub mod parsing {
use super::*;
- use escape::{cooked_string, raw_string};
+ use escape::{cooked_char, cooked_string, raw_string};
use space::whitespace;
use nom::IResult;
@@ -62,8 +62,10 @@
string
|
byte_string
- // TODO: Byte
- // TODO: Char
+ |
+ byte
+ |
+ character
|
int => { |(value, ty)| Lit::Int(value, ty) }
// TODO: Float
@@ -101,6 +103,21 @@
) => { |(s, _): (String, _)| Lit::ByteStr(s.into_bytes()) }
));
+ named!(byte -> Lit, do_parse!(
+ punct!("b") >>
+ tag!("'") >>
+ ch: cooked_char >>
+ tag!("'") >>
+ (Lit::Byte(ch as u8))
+ ));
+
+ named!(character -> Lit, do_parse!(
+ punct!("'") >>
+ ch: cooked_char >>
+ tag!("'") >>
+ (Lit::Char(ch))
+ ));
+
named!(pub int -> (u64, IntTy), tuple!(
preceded!(
option!(whitespace),
@@ -184,7 +201,7 @@
escaped.push('"');
tokens.append(&escaped);
}
- Lit::Byte(b) => tokens.append(&format!("b{:?}", b)),
+ Lit::Byte(b) => tokens.append(&format!("b{:?}", b as char)),
Lit::Char(ch) => ch.to_tokens(tokens),
Lit::Int(value, ty) => tokens.append(&format!("{}{}", value, ty)),
Lit::Float(ref value, ty) => tokens.append(&format!("{}{}", value, ty)),