]> git.proxmox.com Git - rustc.git/blame - src/test/auxiliary/roman_numerals.rs
Imported Upstream version 1.6.0+dfsg1
[rustc.git] / src / test / auxiliary / roman_numerals.rs
CommitLineData
1a4d82fc
JJ
1// Copyright 2014 The Rust Project Developers. See the COPYRIGHT
2// file at the top-level directory of this distribution and at
3// http://rust-lang.org/COPYRIGHT.
4//
5// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8// option. This file may not be copied, modified, or distributed
9// except according to those terms.
10
11// force-host
12
13#![crate_type="dylib"]
c34b1796
AL
14#![feature(plugin_registrar, rustc_private)]
15#![feature(slice_patterns)]
1a4d82fc
JJ
16
17extern crate syntax;
18extern crate rustc;
92a42be0 19extern crate rustc_plugin;
1a4d82fc
JJ
20
21use syntax::codemap::Span;
92a42be0 22use syntax::ast::TokenTree;
c1a9b12d 23use syntax::parse::token;
c34b1796 24use syntax::ext::base::{ExtCtxt, MacResult, DummyResult, MacEager};
85aaf69f 25use syntax::ext::build::AstBuilder; // trait for expr_usize
92a42be0 26use rustc_plugin::Registry;
1a4d82fc
JJ
27
28// WARNING WARNING WARNING WARNING WARNING
29// =======================================
30//
31// This code also appears in src/doc/guide-plugin.md. Please keep
32// the two copies in sync! FIXME: have rustdoc read this file
33
34fn expand_rn(cx: &mut ExtCtxt, sp: Span, args: &[TokenTree])
35 -> Box<MacResult + 'static> {
36
c34b1796 37 static NUMERALS: &'static [(&'static str, usize)] = &[
1a4d82fc
JJ
38 ("M", 1000), ("CM", 900), ("D", 500), ("CD", 400),
39 ("C", 100), ("XC", 90), ("L", 50), ("XL", 40),
40 ("X", 10), ("IX", 9), ("V", 5), ("IV", 4),
41 ("I", 1)];
42
92a42be0
SL
43 if args.len() != 1 {
44 cx.span_err(
45 sp,
46 &format!("argument should be a single identifier, but got {} arguments", args.len()));
47 return DummyResult::any(sp);
48 }
49
50 let text = match args[0] {
51 TokenTree::Token(_, token::Ident(s, _)) => s.to_string(),
1a4d82fc
JJ
52 _ => {
53 cx.span_err(sp, "argument should be a single identifier");
54 return DummyResult::any(sp);
55 }
56 };
57
85aaf69f 58 let mut text = &*text;
c34b1796 59 let mut total = 0;
1a4d82fc
JJ
60 while !text.is_empty() {
61 match NUMERALS.iter().find(|&&(rn, _)| text.starts_with(rn)) {
62 Some(&(rn, val)) => {
63 total += val;
85aaf69f 64 text = &text[rn.len()..];
1a4d82fc
JJ
65 }
66 None => {
67 cx.span_err(sp, "invalid Roman numeral");
68 return DummyResult::any(sp);
69 }
70 }
71 }
72
c34b1796 73 MacEager::expr(cx.expr_usize(sp, total))
1a4d82fc
JJ
74}
75
76#[plugin_registrar]
77pub fn plugin_registrar(reg: &mut Registry) {
78 reg.register_macro("rn", expand_rn);
79}