Merge "Simplify adb LinePrinter newline handling."
This commit is contained in:
commit
9fa5cefea4
3 changed files with 33 additions and 89 deletions
|
|
@ -76,6 +76,8 @@ class SyncConnection {
|
||||||
ReadOrderlyShutdown(fd);
|
ReadOrderlyShutdown(fd);
|
||||||
}
|
}
|
||||||
adb_close(fd);
|
adb_close(fd);
|
||||||
|
|
||||||
|
line_printer_.KeepInfoLine();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool IsValid() { return fd >= 0; }
|
bool IsValid() { return fd >= 0; }
|
||||||
|
|
@ -243,8 +245,7 @@ class SyncConnection {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Print(const std::string& s) {
|
void Print(const std::string& s) {
|
||||||
// TODO: we actually don't want ELIDE; we want "ELIDE if smart, FULL if dumb".
|
line_printer_.Print(s, LinePrinter::INFO);
|
||||||
line_printer_.Print(s, LinePrinter::ELIDE);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Printf(const char* fmt, ...) __attribute__((__format__(ADB_FORMAT_ARCHETYPE, 2, 3))) {
|
void Printf(const char* fmt, ...) __attribute__((__format__(ADB_FORMAT_ARCHETYPE, 2, 3))) {
|
||||||
|
|
@ -265,7 +266,7 @@ class SyncConnection {
|
||||||
android::base::StringAppendV(&s, fmt, ap);
|
android::base::StringAppendV(&s, fmt, ap);
|
||||||
va_end(ap);
|
va_end(ap);
|
||||||
|
|
||||||
line_printer_.Print(s, LinePrinter::FULL);
|
line_printer_.Print(s, LinePrinter::ERROR);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Warning(const char* fmt, ...) __attribute__((__format__(ADB_FORMAT_ARCHETYPE, 2, 3))) {
|
void Warning(const char* fmt, ...) __attribute__((__format__(ADB_FORMAT_ARCHETYPE, 2, 3))) {
|
||||||
|
|
@ -276,7 +277,7 @@ class SyncConnection {
|
||||||
android::base::StringAppendV(&s, fmt, ap);
|
android::base::StringAppendV(&s, fmt, ap);
|
||||||
va_end(ap);
|
va_end(ap);
|
||||||
|
|
||||||
line_printer_.Print(s, LinePrinter::FULL);
|
line_printer_.Print(s, LinePrinter::WARNING);
|
||||||
}
|
}
|
||||||
|
|
||||||
uint64_t total_bytes;
|
uint64_t total_bytes;
|
||||||
|
|
@ -664,7 +665,7 @@ static bool copy_local_dir_remote(SyncConnection& sc, std::string lpath,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
sc.Printf("%s: %d file%s pushed. %d file%s skipped.%s\n", rpath.c_str(),
|
sc.Printf("%s: %d file%s pushed. %d file%s skipped.%s", rpath.c_str(),
|
||||||
pushed, (pushed == 1) ? "" : "s", skipped,
|
pushed, (pushed == 1) ? "" : "s", skipped,
|
||||||
(skipped == 1) ? "" : "s", sc.TransferRate().c_str());
|
(skipped == 1) ? "" : "s", sc.TransferRate().c_str());
|
||||||
return true;
|
return true;
|
||||||
|
|
@ -739,7 +740,6 @@ bool do_sync_push(const std::vector<const char*>& srcs, const char* dst) {
|
||||||
success &= sync_send(sc, src_path, dst_path, st.st_mtime, st.st_mode);
|
success &= sync_send(sc, src_path, dst_path, st.st_mtime, st.st_mode);
|
||||||
}
|
}
|
||||||
|
|
||||||
sc.Print("\n");
|
|
||||||
return success;
|
return success;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -858,7 +858,7 @@ static bool copy_remote_dir_local(SyncConnection& sc, std::string rpath,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
sc.Printf("%s: %d file%s pulled. %d file%s skipped.%s\n", rpath.c_str(),
|
sc.Printf("%s: %d file%s pulled. %d file%s skipped.%s", rpath.c_str(),
|
||||||
pulled, (pulled == 1) ? "" : "s", skipped,
|
pulled, (pulled == 1) ? "" : "s", skipped,
|
||||||
(skipped == 1) ? "" : "s", sc.TransferRate().c_str());
|
(skipped == 1) ? "" : "s", sc.TransferRate().c_str());
|
||||||
return true;
|
return true;
|
||||||
|
|
@ -967,7 +967,6 @@ bool do_sync_pull(const std::vector<const char*>& srcs, const char* dst,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
sc.Print("\n");
|
|
||||||
return success;
|
return success;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -43,7 +43,7 @@ string ElideMiddle(const string& str, size_t width) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
LinePrinter::LinePrinter() : have_blank_line_(true), console_locked_(false) {
|
LinePrinter::LinePrinter() : have_blank_line_(true) {
|
||||||
#ifndef _WIN32
|
#ifndef _WIN32
|
||||||
const char* term = getenv("TERM");
|
const char* term = getenv("TERM");
|
||||||
smart_terminal_ = unix_isatty(1) && term && string(term) != "dumb";
|
smart_terminal_ = unix_isatty(1) && term && string(term) != "dumb";
|
||||||
|
|
@ -59,20 +59,24 @@ LinePrinter::LinePrinter() : have_blank_line_(true), console_locked_(false) {
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void Out(const std::string& s) {
|
||||||
|
// Avoid printf and C strings, since the actual output might contain null
|
||||||
|
// bytes like UTF-16 does (yuck).
|
||||||
|
fwrite(s.data(), 1, s.size(), stdout);
|
||||||
|
}
|
||||||
|
|
||||||
void LinePrinter::Print(string to_print, LineType type) {
|
void LinePrinter::Print(string to_print, LineType type) {
|
||||||
if (console_locked_) {
|
if (!smart_terminal_) {
|
||||||
line_buffer_ = to_print;
|
Out(to_print);
|
||||||
line_type_ = type;
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (smart_terminal_) {
|
// Print over previous line, if any.
|
||||||
printf("\r"); // Print over previous line, if any.
|
// On Windows, calling a C library function writing to stdout also handles
|
||||||
// On Windows, calling a C library function writing to stdout also handles
|
// pausing the executable when the "Pause" key or Ctrl-S is pressed.
|
||||||
// pausing the executable when the "Pause" key or Ctrl-S is pressed.
|
printf("\r");
|
||||||
}
|
|
||||||
|
|
||||||
if (smart_terminal_ && type == ELIDE) {
|
if (type == INFO) {
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
CONSOLE_SCREEN_BUFFER_INFO csbi;
|
CONSOLE_SCREEN_BUFFER_INFO csbi;
|
||||||
GetConsoleScreenBufferInfo(console_, &csbi);
|
GetConsoleScreenBufferInfo(console_, &csbi);
|
||||||
|
|
@ -105,57 +109,19 @@ void LinePrinter::Print(string to_print, LineType type) {
|
||||||
if ((ioctl(0, TIOCGWINSZ, &size) == 0) && size.ws_col) {
|
if ((ioctl(0, TIOCGWINSZ, &size) == 0) && size.ws_col) {
|
||||||
to_print = ElideMiddle(to_print, size.ws_col);
|
to_print = ElideMiddle(to_print, size.ws_col);
|
||||||
}
|
}
|
||||||
printf("%s", to_print.c_str());
|
Out(to_print);
|
||||||
printf("\x1B[K"); // Clear to end of line.
|
printf("\x1B[K"); // Clear to end of line.
|
||||||
fflush(stdout);
|
fflush(stdout);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
have_blank_line_ = false;
|
have_blank_line_ = false;
|
||||||
} else {
|
} else {
|
||||||
printf("%s\n", to_print.c_str());
|
Out(to_print);
|
||||||
|
Out("\n");
|
||||||
|
have_blank_line_ = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void LinePrinter::PrintOrBuffer(const char* data, size_t size) {
|
void LinePrinter::KeepInfoLine() {
|
||||||
if (console_locked_) {
|
if (!have_blank_line_) Out("\n");
|
||||||
output_buffer_.append(data, size);
|
|
||||||
} else {
|
|
||||||
// Avoid printf and C strings, since the actual output might contain null
|
|
||||||
// bytes like UTF-16 does (yuck).
|
|
||||||
fwrite(data, 1, size, stdout);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void LinePrinter::PrintOnNewLine(const string& to_print) {
|
|
||||||
if (console_locked_ && !line_buffer_.empty()) {
|
|
||||||
output_buffer_.append(line_buffer_);
|
|
||||||
output_buffer_.append(1, '\n');
|
|
||||||
line_buffer_.clear();
|
|
||||||
}
|
|
||||||
if (!have_blank_line_) {
|
|
||||||
PrintOrBuffer("\n", 1);
|
|
||||||
}
|
|
||||||
if (!to_print.empty()) {
|
|
||||||
PrintOrBuffer(&to_print[0], to_print.size());
|
|
||||||
}
|
|
||||||
have_blank_line_ = to_print.empty() || *to_print.rbegin() == '\n';
|
|
||||||
}
|
|
||||||
|
|
||||||
void LinePrinter::SetConsoleLocked(bool locked) {
|
|
||||||
if (locked == console_locked_)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (locked)
|
|
||||||
PrintOnNewLine("");
|
|
||||||
|
|
||||||
console_locked_ = locked;
|
|
||||||
|
|
||||||
if (!locked) {
|
|
||||||
PrintOnNewLine(output_buffer_);
|
|
||||||
if (!line_buffer_.empty()) {
|
|
||||||
Print(line_buffer_, line_type_);
|
|
||||||
}
|
|
||||||
output_buffer_.clear();
|
|
||||||
line_buffer_.clear();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -26,20 +26,14 @@ struct LinePrinter {
|
||||||
bool is_smart_terminal() const { return smart_terminal_; }
|
bool is_smart_terminal() const { return smart_terminal_; }
|
||||||
void set_smart_terminal(bool smart) { smart_terminal_ = smart; }
|
void set_smart_terminal(bool smart) { smart_terminal_ = smart; }
|
||||||
|
|
||||||
enum LineType {
|
enum LineType { INFO, WARNING, ERROR };
|
||||||
FULL,
|
|
||||||
ELIDE
|
/// Outputs the given line. INFO output will be overwritten.
|
||||||
};
|
/// WARNING and ERROR appear on a line to themselves.
|
||||||
/// Overprints the current line. If type is ELIDE, elides to_print to fit on
|
|
||||||
/// one line.
|
|
||||||
void Print(std::string to_print, LineType type);
|
void Print(std::string to_print, LineType type);
|
||||||
|
|
||||||
/// Prints a string on a new line, not overprinting previous output.
|
/// If there's an INFO line, keep it. If not, do nothing.
|
||||||
void PrintOnNewLine(const std::string& to_print);
|
void KeepInfoLine();
|
||||||
|
|
||||||
/// Lock or unlock the console. Any output sent to the LinePrinter while the
|
|
||||||
/// console is locked will not be printed until it is unlocked.
|
|
||||||
void SetConsoleLocked(bool locked);
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/// Whether we can do fancy terminal control codes.
|
/// Whether we can do fancy terminal control codes.
|
||||||
|
|
@ -48,24 +42,9 @@ struct LinePrinter {
|
||||||
/// Whether the caret is at the beginning of a blank line.
|
/// Whether the caret is at the beginning of a blank line.
|
||||||
bool have_blank_line_;
|
bool have_blank_line_;
|
||||||
|
|
||||||
/// Whether console is locked.
|
|
||||||
bool console_locked_;
|
|
||||||
|
|
||||||
/// Buffered current line while console is locked.
|
|
||||||
std::string line_buffer_;
|
|
||||||
|
|
||||||
/// Buffered line type while console is locked.
|
|
||||||
LineType line_type_;
|
|
||||||
|
|
||||||
/// Buffered console output while console is locked.
|
|
||||||
std::string output_buffer_;
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
void* console_;
|
void* console_;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/// Print the given data to the console, or buffer it if it is locked.
|
|
||||||
void PrintOrBuffer(const char *data, size_t size);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // NINJA_LINE_PRINTER_H_
|
#endif // NINJA_LINE_PRINTER_H_
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue