blob: 89f7b102606b8327d807ca58528b4427cf2b3261 [file] [log] [blame]
David Tolnaye5806852017-06-01 12:49:20 -07001extern crate proc_macro2;
2
David Tolnay79105e52017-12-31 11:03:04 -05003use proc_macro2::{Term, Literal, TokenStream};
4
David Tolnay1ebe3972018-01-02 20:14:20 -08005#[cfg(procmacro2_semver_exempt)]
David Tolnay79105e52017-12-31 11:03:04 -05006use proc_macro2::TokenNode;
7
David Tolnay1ebe3972018-01-02 20:14:20 -08008#[cfg(procmacro2_semver_exempt)]
David Tolnayd66ecf62018-01-02 20:05:42 -08009#[cfg(not(feature = "nightly"))]
David Tolnay79105e52017-12-31 11:03:04 -050010use proc_macro2::Span;
David Tolnaye5806852017-06-01 12:49:20 -070011
12#[test]
13fn symbols() {
Alex Crichton1a7f7622017-07-05 17:47:15 -070014 assert_eq!(Term::intern("foo").as_str(), "foo");
15 assert_eq!(Term::intern("bar").as_str(), "bar");
David Tolnaye5806852017-06-01 12:49:20 -070016}
17
18#[test]
19fn literals() {
Alex Crichton1a7f7622017-07-05 17:47:15 -070020 assert_eq!(Literal::string("foo").to_string(), "\"foo\"");
21 assert_eq!(Literal::string("\"").to_string(), "\"\\\"\"");
David Tolnaye5806852017-06-01 12:49:20 -070022}
23
24#[test]
25fn roundtrip() {
26 fn roundtrip(p: &str) {
27 println!("parse: {}", p);
28 let s = p.parse::<TokenStream>().unwrap().to_string();
29 println!("first: {}", s);
30 let s2 = s.to_string().parse::<TokenStream>().unwrap().to_string();
31 assert_eq!(s, s2);
32 }
33 roundtrip("a");
34 roundtrip("<<");
35 roundtrip("<<=");
36 roundtrip("
37 /// a
38 wut
39 ");
40 roundtrip("
41 1
42 1.0
43 1f32
44 2f64
45 1usize
46 4isize
47 4e10
48 1_000
49 1_0i32
50 8u8
51 9
52 0
53 0xffffffffffffffffffffffffffffffff
54 ");
55 roundtrip("'a");
56 roundtrip("'static");
David Tolnay8d109342017-12-25 18:24:45 -050057 roundtrip("'\\u{10__FFFF}'");
58 roundtrip("\"\\u{10_F0FF__}foo\\u{1_0_0_0__}\"");
David Tolnaye5806852017-06-01 12:49:20 -070059}
60
61#[test]
62fn fail() {
63 fn fail(p: &str) {
64 if p.parse::<TokenStream>().is_ok() {
65 panic!("should have failed to parse: {}", p);
66 }
67 }
68 fail("1x");
69 fail("1u80");
70 fail("1f320");
71 fail("' static");
72 fail("'mut");
73}
Nika Layzellf8d5f212017-12-11 14:07:02 -050074
David Tolnay1ebe3972018-01-02 20:14:20 -080075#[cfg(procmacro2_semver_exempt)]
Nika Layzellf8d5f212017-12-11 14:07:02 -050076#[test]
77fn span_test() {
78 fn check_spans(p: &str, mut lines: &[(usize, usize, usize, usize)]) {
Nika Layzellf8d5f212017-12-11 14:07:02 -050079 let ts = p.parse::<TokenStream>().unwrap();
80 check_spans_internal(ts, &mut lines);
81 }
82
83 fn check_spans_internal(
84 ts: TokenStream,
85 lines: &mut &[(usize, usize, usize, usize)],
86 ) {
87 for i in ts {
88 if let Some((&(sline, scol, eline, ecol), rest)) = lines.split_first() {
89 *lines = rest;
90
Nika Layzellf8d5f212017-12-11 14:07:02 -050091 let start = i.span.start();
92 assert_eq!(start.line, sline, "sline did not match for {}", i);
93 assert_eq!(start.column, scol, "scol did not match for {}", i);
94
95 let end = i.span.end();
96 assert_eq!(end.line, eline, "eline did not match for {}", i);
97 assert_eq!(end.column, ecol, "ecol did not match for {}", i);
98
99 match i.kind {
100 TokenNode::Group(_, stream) =>
101 check_spans_internal(stream, lines),
102 _ => {}
103 }
104 }
105 }
106 }
107
108 check_spans("\
109/// This is a document comment
110testing 123
111{
112 testing 234
113}", &[
114 (1, 0, 1, 30),
115 (2, 0, 2, 7),
116 (2, 8, 2, 11),
117 (3, 0, 5, 1),
118 (4, 2, 4, 9),
119 (4, 10, 4, 13),
120]);
121}
122
David Tolnay1ebe3972018-01-02 20:14:20 -0800123#[cfg(procmacro2_semver_exempt)]
David Tolnayd66ecf62018-01-02 20:05:42 -0800124#[cfg(not(feature = "nightly"))]
Nika Layzellf8d5f212017-12-11 14:07:02 -0500125#[test]
126fn default_span() {
127 let start = Span::call_site().start();
128 assert_eq!(start.line, 1);
129 assert_eq!(start.column, 0);
130 let end = Span::call_site().end();
131 assert_eq!(end.line, 1);
132 assert_eq!(end.column, 0);
133 let source_file = Span::call_site().source_file();
Nika Layzellfb783e32017-12-30 14:58:27 -0500134 assert_eq!(source_file.path().to_string(), "<unspecified>");
Nika Layzellf8d5f212017-12-11 14:07:02 -0500135 assert!(!source_file.is_real());
136}
137
David Tolnay1ebe3972018-01-02 20:14:20 -0800138#[cfg(procmacro2_semver_exempt)]
Nika Layzellddea1562017-12-11 14:25:35 -0500139#[test]
140fn span_join() {
141 let source1 =
142 "aaa\nbbb".parse::<TokenStream>().unwrap().into_iter().collect::<Vec<_>>();
143 let source2 =
144 "ccc\nddd".parse::<TokenStream>().unwrap().into_iter().collect::<Vec<_>>();
145
146 assert!(source1[0].span.source_file() != source2[0].span.source_file());
147 assert_eq!(source1[0].span.source_file(), source1[1].span.source_file());
148
149 let joined1 = source1[0].span.join(source1[1].span);
150 let joined2 = source1[0].span.join(source2[0].span);
151 assert!(joined1.is_some());
152 assert!(joined2.is_none());
153
154 let start = joined1.unwrap().start();
155 let end = joined1.unwrap().end();
156 assert_eq!(start.line, 1);
157 assert_eq!(start.column, 0);
158 assert_eq!(end.line, 2);
159 assert_eq!(end.column, 3);
160
161 assert_eq!(joined1.unwrap().source_file(), source1[0].span.source_file());
162}