Variadic functions
diff --git a/src/expr.rs b/src/expr.rs
index d650e22..126b4d4 100644
--- a/src/expr.rs
+++ b/src/expr.rs
@@ -648,6 +648,7 @@
             Box::new(FnDecl {
                 inputs: inputs,
                 output: ret_and_body.0,
+                variadic: false,
             }),
             ret_and_body.1,
         ))
diff --git a/src/item.rs b/src/item.rs
index f87c459..273f1c5 100644
--- a/src/item.rs
+++ b/src/item.rs
@@ -217,6 +217,7 @@
 pub struct FnDecl {
     pub inputs: Vec<FnArg>,
     pub output: FunctionRetTy,
+    pub variadic: bool,
 }
 
 /// An argument in a function header.
@@ -453,6 +454,7 @@
                 Box::new(FnDecl {
                     inputs: inputs,
                     output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
+                    variadic: false,
                 }),
                 unsafety,
                 constness,
@@ -560,7 +562,9 @@
         name: ident >>
         generics: generics >>
         punct!("(") >>
-        inputs: terminated_list!(punct!(","), fn_arg) >>
+        inputs: separated_list!(punct!(","), fn_arg) >>
+        trailing_comma: option!(punct!(",")) >>
+        variadic: option!(cond_reduce!(trailing_comma.is_some(), punct!("..."))) >>
         punct!(")") >>
         ret: option!(preceded!(punct!("->"), ty)) >>
         where_clause: where_clause >>
@@ -572,6 +576,7 @@
                 Box::new(FnDecl {
                     inputs: inputs,
                     output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
+                    variadic: variadic.is_some(),
                 }),
                 Generics {
                     where_clause: where_clause,
@@ -754,6 +759,7 @@
                     decl: FnDecl {
                         inputs: inputs,
                         output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
+                        variadic: false,
                     },
                     generics: Generics {
                         where_clause: where_clause,
@@ -898,6 +904,7 @@
                     decl: FnDecl {
                         inputs: inputs,
                         output: ret.map(FunctionRetTy::Ty).unwrap_or(FunctionRetTy::Default),
+                        variadic: false,
                     },
                     generics: Generics {
                         where_clause: where_clause,
@@ -1330,6 +1337,12 @@
                     generics.to_tokens(tokens);
                     tokens.append("(");
                     tokens.append_separated(&decl.inputs, ",");
+                    if decl.variadic {
+                        if !decl.inputs.is_empty() {
+                            tokens.append(",");
+                        }
+                        tokens.append("...");
+                    }
                     tokens.append(")");
                     if let FunctionRetTy::Ty(ref ty) = decl.output {
                         tokens.append("->");
diff --git a/src/ty.rs b/src/ty.rs
index 2d29dee..5eab736 100644
--- a/src/ty.rs
+++ b/src/ty.rs
@@ -171,6 +171,7 @@
     pub lifetimes: Vec<LifetimeDef>,
     pub inputs: Vec<BareFnArg>,
     pub output: FunctionRetTy,
+    pub variadic: bool,
 }
 
 #[derive(Debug, Copy, Clone, Eq, PartialEq)]
@@ -293,7 +294,9 @@
         abi: option!(abi) >>
         keyword!("fn") >>
         punct!("(") >>
-        inputs: terminated_list!(punct!(","), fn_arg) >>
+        inputs: separated_list!(punct!(","), fn_arg) >>
+        trailing_comma: option!(punct!(",")) >>
+        variadic: option!(cond_reduce!(trailing_comma.is_some(), punct!("..."))) >>
         punct!(")") >>
         output: option!(preceded!(
             punct!("->"),
@@ -308,6 +311,7 @@
                 Some(ty) => FunctionRetTy::Ty(ty),
                 None => FunctionRetTy::Default,
             },
+            variadic: variadic.is_some(),
         })))
     ));
 
@@ -754,6 +758,12 @@
             tokens.append("fn");
             tokens.append("(");
             tokens.append_separated(&self.inputs, ",");
+            if self.variadic {
+                if !self.inputs.is_empty() {
+                    tokens.append(",");
+                }
+                tokens.append("...");
+            }
             tokens.append(")");
             if let FunctionRetTy::Ty(ref ty) = self.output {
                 tokens.append("->");