merge in nyc-dr1-release history after reset to nyc-mr1-dev
diff --git a/error_code.h b/error_code.h
index 259319a..fe38ba4 100644
--- a/error_code.h
+++ b/error_code.h
@@ -21,7 +21,8 @@
     kNoError = -1,
     kLowBattery = 20,
     kZipVerificationFailure,
-    kZipOpenFailure
+    kZipOpenFailure,
+    kBootreasonInBlacklist
 };
 
 enum CauseCode {
diff --git a/recovery.cpp b/recovery.cpp
index c4b3655..cd4f361 100644
--- a/recovery.cpp
+++ b/recovery.cpp
@@ -89,6 +89,12 @@
   { NULL, 0, NULL, 0 },
 };
 
+// More bootreasons can be found in "system/core/bootstat/bootstat.cpp".
+static const std::vector<std::string> bootreason_blacklist {
+  "kernel_panic",
+  "Panic",
+};
+
 static const char *CACHE_LOG_DIR = "/cache/recovery";
 static const char *COMMAND_FILE = "/cache/recovery/command";
 static const char *INTENT_FILE = "/cache/recovery/intent";
@@ -1405,6 +1411,30 @@
     }
 }
 
+static bool bootreason_in_blacklist() {
+    char bootreason[PROPERTY_VALUE_MAX];
+    if (property_get("ro.boot.bootreason", bootreason, nullptr) > 0) {
+        for (const auto& str : bootreason_blacklist) {
+            if (strcasecmp(str.c_str(), bootreason) == 0) {
+                return true;
+            }
+        }
+    }
+    return false;
+}
+
+static void log_failure_code(ErrorCode code, const char *update_package) {
+    FILE* install_log = fopen_path(TEMPORARY_INSTALL_FILE, "w");
+    if (install_log != nullptr) {
+        fprintf(install_log, "%s\n", update_package);
+        fprintf(install_log, "0\n");
+        fprintf(install_log, "error: %d\n", code);
+        fclose(install_log);
+    } else {
+        LOGE("failed to open last_install: %s\n", strerror(errno));
+    }
+}
+
 static ssize_t logbasename(
         log_id_t /* logId */,
         char /* prio */,
@@ -1628,15 +1658,12 @@
                       BATTERY_OK_PERCENTAGE);
             // Log the error code to last_install when installation skips due to
             // low battery.
-            FILE* install_log = fopen_path(LAST_INSTALL_FILE, "w");
-            if (install_log != nullptr) {
-                fprintf(install_log, "%s\n", update_package);
-                fprintf(install_log, "0\n");
-                fprintf(install_log, "error: %d\n", kLowBattery);
-                fclose(install_log);
-            } else {
-                LOGE("failed to open last_install: %s\n", strerror(errno));
-            }
+            log_failure_code(kLowBattery, update_package);
+            status = INSTALL_SKIPPED;
+        } else if (bootreason_in_blacklist()) {
+            // Skip update-on-reboot when bootreason is kernel_panic or similar
+            ui->Print("bootreason is in the blacklist; skip OTA installation\n");
+            log_failure_code(kBootreasonInBlacklist, update_package);
             status = INSTALL_SKIPPED;
         } else {
             status = install_package(update_package, &should_wipe_cache,
diff --git a/screen_ui.cpp b/screen_ui.cpp
index 85f789f..2a0769e 100644
--- a/screen_ui.cpp
+++ b/screen_ui.cpp
@@ -105,29 +105,41 @@
 
 // Here's the intended layout:
 
-//          | regular     large
-// ---------+--------------------
-//          |   220dp     366dp
-// icon     |  (200dp)   (200dp)
-//          |    68dp      68dp
-// text     |   (14sp)    (14sp)
-//          |    32dp      32dp
-// progress |    (2dp)     (2dp)
-//          |   194dp     340dp
+//          | portrait    large        landscape      large
+// ---------+-------------------------------------------------
+//      gap |   220dp     366dp            142dp      284dp
+// icon     |                   (200dp)
+//      gap |    68dp      68dp             56dp      112dp
+// text     |                    (14sp)
+//      gap |    32dp      32dp             26dp       52dp
+// progress |                     (2dp)
+//      gap |   194dp     340dp            131dp      262dp
 
 // Note that "baseline" is actually the *top* of each icon (because that's how our drawing
 // routines work), so that's the more useful measurement for calling code.
 
+enum Layout { PORTRAIT = 0, PORTRAIT_LARGE = 1, LANDSCAPE = 2, LANDSCAPE_LARGE = 3, LAYOUT_MAX };
+enum Dimension { PROGRESS = 0, TEXT = 1, ICON = 2, DIMENSION_MAX };
+static constexpr int kLayouts[LAYOUT_MAX][DIMENSION_MAX] = {
+    { 194,  32,  68, }, // PORTRAIT
+    { 340,  32,  68, }, // PORTRAIT_LARGE
+    { 131,  26,  56, }, // LANDSCAPE
+    { 262,  52, 112, }, // LANDSCAPE_LARGE
+};
+
 int ScreenRecoveryUI::GetAnimationBaseline() {
-    return GetTextBaseline() - PixelsFromDp(68) - gr_get_height(loopFrames[0]);
+    return GetTextBaseline() - PixelsFromDp(kLayouts[layout_][ICON]) -
+            gr_get_height(loopFrames[0]);
 }
 
 int ScreenRecoveryUI::GetTextBaseline() {
-    return GetProgressBaseline() - PixelsFromDp(32) - gr_get_height(installing_text);
+    return GetProgressBaseline() - PixelsFromDp(kLayouts[layout_][TEXT]) -
+            gr_get_height(installing_text);
 }
 
 int ScreenRecoveryUI::GetProgressBaseline() {
-    return gr_fb_height() - PixelsFromDp(is_large_ ? 340 : 194) - gr_get_height(progressBarFill);
+    return gr_fb_height() - PixelsFromDp(kLayouts[layout_][PROGRESS]) -
+            gr_get_height(progressBarFill);
 }
 
 // Clear the screen and draw the currently selected background icon (if any).
@@ -439,7 +451,11 @@
     gr_init();
 
     density_ = static_cast<float>(property_get_int32("ro.sf.lcd_density", 160)) / 160.f;
-    is_large_ = gr_fb_height() > PixelsFromDp(800);
+
+    // Are we portrait or landscape?
+    layout_ = (gr_fb_width() > gr_fb_height()) ? LANDSCAPE : PORTRAIT;
+    // Are we the large variant of our base layout?
+    if (gr_fb_height() > PixelsFromDp(800)) ++layout_;
 
     gr_font_size(&char_width_, &char_height_);
     text_rows_ = gr_fb_height() / char_height_;
diff --git a/screen_ui.h b/screen_ui.h
index 4319b76..8987757 100644
--- a/screen_ui.h
+++ b/screen_ui.h
@@ -77,8 +77,8 @@
 
     // The scale factor from dp to pixels. 1.0 for mdpi, 4.0 for xxxhdpi.
     float density_;
-    // True if we should use the large layout.
-    bool is_large_;
+    // The layout to use.
+    int layout_;
 
     GRSurface* error_icon;