aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/comp/front/extfmt.rs30
-rw-r--r--src/lib/ExtFmt.rs11
-rw-r--r--src/test/run-pass/syntax-extension-fmt.rs5
3 files changed, 40 insertions, 6 deletions
diff --git a/src/comp/front/extfmt.rs b/src/comp/front/extfmt.rs
index 3aa24a90..c05c74d1 100644
--- a/src/comp/front/extfmt.rs
+++ b/src/comp/front/extfmt.rs
@@ -29,7 +29,7 @@ import std.ExtFmt.CT.flag;
import std.ExtFmt.CT.flag_left_justify;
import std.ExtFmt.CT.flag_left_zero_pad;
import std.ExtFmt.CT.flag_left_space_pad;
-import std.ExtFmt.CT.flag_plus_if_positive;
+import std.ExtFmt.CT.flag_sign_always;
import std.ExtFmt.CT.flag_alternate;
import std.ExtFmt.CT.count;
import std.ExtFmt.CT.count_is;
@@ -176,6 +176,10 @@ fn pieces_to_expr(vec[piece] pieces, vec[@ast.expr] args) -> @ast.expr {
auto fstr = "flag_left_justify";
flagexprs += vec(make_rt_path_expr(sp, fstr));
}
+ case (flag_sign_always) {
+ auto fstr = "flag_sign_always";
+ flagexprs += vec(make_rt_path_expr(sp, fstr));
+ }
}
}
@@ -279,6 +283,26 @@ fn pieces_to_expr(vec[piece] pieces, vec[@ast.expr] args) -> @ast.expr {
alt (f) {
case (flag_left_justify) {
}
+ case (flag_sign_always) {
+ auto err = "+ flag only valid in signed #fmt conversions";
+ alt (cnv.ty) {
+ case (ty_int(?s)) {
+ alt (s) {
+ case (signed) {
+ // Valid
+ }
+ case (unsigned) {
+ log err;
+ fail;
+ }
+ }
+ }
+ case (_) {
+ log err;
+ fail;
+ }
+ }
+ }
case (_) {
log unsupported;
fail;
@@ -361,8 +385,8 @@ fn pieces_to_expr(vec[piece] pieces, vec[@ast.expr] args) -> @ast.expr {
case (flag_left_space_pad) {
log "flag: left space pad";
}
- case (flag_plus_if_positive) {
- log "flag: plus if positive";
+ case (flag_sign_always) {
+ log "flag: sign always";
}
case (flag_alternate) {
log "flag: alternate";
diff --git a/src/lib/ExtFmt.rs b/src/lib/ExtFmt.rs
index 4be03858..c2cce279 100644
--- a/src/lib/ExtFmt.rs
+++ b/src/lib/ExtFmt.rs
@@ -53,7 +53,7 @@ mod CT {
flag_left_justify;
flag_left_zero_pad;
flag_left_space_pad;
- flag_plus_if_positive;
+ flag_sign_always;
flag_alternate;
}
@@ -203,7 +203,7 @@ mod CT {
} else if (f == (' ' as u8)) {
ret more(flag_left_space_pad);
} else if (f == ('+' as u8)) {
- ret more(flag_plus_if_positive);
+ ret more(flag_sign_always);
} else if (f == ('#' as u8)) {
ret more(flag_alternate);
} else {
@@ -306,6 +306,7 @@ mod RT {
tag flag {
flag_left_justify;
+ flag_sign_always;
// FIXME: This is a hack to avoid creating 0-length vec exprs,
// which have some difficulty typechecking currently. See
// comments in front.extfmt.make_flags
@@ -334,7 +335,11 @@ mod RT {
fn conv_int(&conv cv, int i) -> str {
auto radix = 10u;
auto prec = get_int_precision(cv);
- ret pad(cv, int_to_str_prec(i, radix, prec));
+ auto s = int_to_str_prec(i, radix, prec);
+ if (0 <= i && have_flag(cv.flags, flag_sign_always)) {
+ s = "+" + s;
+ }
+ ret pad(cv, s);
}
fn conv_uint(&conv cv, uint u) -> str {
diff --git a/src/test/run-pass/syntax-extension-fmt.rs b/src/test/run-pass/syntax-extension-fmt.rs
index 5c66b17a..1e283c2d 100644
--- a/src/test/run-pass/syntax-extension-fmt.rs
+++ b/src/test/run-pass/syntax-extension-fmt.rs
@@ -112,4 +112,9 @@ fn main() {
test(#fmt("%.b", true), "");
test(#fmt("%.0b", true), "");
test(#fmt("%.1b", true), "t");
+
+ // Explicit + sign. Only for signed conversions
+ test(#fmt("%+d", 0), "+0");
+ test(#fmt("%+d", 1), "+1");
+ test(#fmt("%+d", -1), "-1");
}