diff --git a/src/lint/linter/ArcanistXHPASTLinter.php b/src/lint/linter/ArcanistXHPASTLinter.php
--- a/src/lint/linter/ArcanistXHPASTLinter.php
+++ b/src/lint/linter/ArcanistXHPASTLinter.php
@@ -48,6 +48,7 @@
   const LINT_LANGUAGE_CONSTRUCT_PAREN  = 46;
   const LINT_EMPTY_STATEMENT           = 47;
   const LINT_ARRAY_SEPARATOR           = 48;
+  const LINT_ONE_STATEMENT_PER_LINE    = 49;
 
   private $naminghook;
   private $switchhook;
@@ -107,6 +108,7 @@
       self::LINT_LANGUAGE_CONSTRUCT_PAREN  => 'Language Construct Parentheses',
       self::LINT_EMPTY_STATEMENT           => 'Empty Block Statement',
       self::LINT_ARRAY_SEPARATOR           => 'Array Separator',
+      self::LINT_ONE_STATEMENT_PER_LINE    => 'One Statement Per Line',
     );
   }
 
@@ -147,6 +149,7 @@
       self::LINT_LANGUAGE_CONSTRUCT_PAREN  => $warning,
       self::LINT_EMPTY_STATEMENT           => $advice,
       self::LINT_ARRAY_SEPARATOR           => $advice,
+      self::LINT_ONE_STATEMENT_PER_LINE    => $advice,
     );
   }
 
@@ -196,7 +199,7 @@
 
   public function getVersion() {
     // The version number should be incremented whenever a new rule is added.
-    return '9';
+    return '10';
   }
 
   protected function resolveFuture($path, Future $future) {
@@ -267,6 +270,7 @@
       'lintLanguageConstructParentheses' => self::LINT_LANGUAGE_CONSTRUCT_PAREN,
       'lintEmptyBlockStatements' => self::LINT_EMPTY_STATEMENT,
       'lintArraySeparator' => self::LINT_ARRAY_SEPARATOR,
+      'lintStatements' => self::LINT_ONE_STATEMENT_PER_LINE,
     );
 
     foreach ($method_codes as $method => $codes) {
@@ -2760,6 +2764,31 @@
     }
   }
 
+  protected function lintStatements(XHPASTNode $root) {
+    $statements = $root->selectDescendantsOfType('n_STATEMENT');
+
+    $line = null;
+    $indent = null;
+
+    foreach ($statements as $statement) {
+      if ($line == $statement->getLineNumber()) {
+        $this->raiseLintAtNode(
+          $statement,
+          self::LINT_ONE_STATEMENT_PER_LINE,
+          pht('Multiple statements on a single line.'),
+          "\n".$indent.$statement->getConcreteString());
+      }
+
+      $line = $statement->getLineNumber();
+      list($before, $after) = $statement->getSurroundingNonsemanticTokens();
+
+      $indent = '';
+      foreach ($before as $token) {
+        $indent .= preg_replace("/^\s*\n/", '', $token->getValue());
+      }
+    }
+  }
+
   public function getSuperGlobalNames() {
     return array(
       '$GLOBALS',
diff --git a/src/lint/linter/__tests__/xhpast/one-statement-per-line.lint-test b/src/lint/linter/__tests__/xhpast/one-statement-per-line.lint-test
new file mode 100644
--- /dev/null
+++ b/src/lint/linter/__tests__/xhpast/one-statement-per-line.lint-test
@@ -0,0 +1,20 @@
+<?php
+foo(); bar(); baz();
+function x() {
+  foo(); bar(); baz();
+}
+~~~~~~~~~~
+advice:2:8
+advice:2:15
+advice:4:10
+advice:4:17
+~~~~~~~~~~
+<?php
+foo();
+bar();
+baz();
+function x() {
+  foo();
+  bar();
+  baz();
+}