root/arch/powerpc/xmon/nonstdio.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. xmon_start_pagination
  2. xmon_end_pagination
  3. xmon_set_pagination_lpp
  4. xmon_readchar
  5. xmon_write
  6. xmon_putchar
  7. xmon_getchar
  8. xmon_gets
  9. xmon_printf
  10. xmon_puts

   1 // SPDX-License-Identifier: GPL-2.0-or-later
   2 /*
   3  * Copyright (C) 1996-2005 Paul Mackerras.
   4  */
   5 #include <linux/string.h>
   6 #include <asm/udbg.h>
   7 #include <asm/time.h>
   8 #include "nonstdio.h"
   9 
  10 static bool paginating, paginate_skipping;
  11 static unsigned long paginate_lpp; /* Lines Per Page */
  12 static unsigned long paginate_pos;
  13 
  14 void xmon_start_pagination(void)
  15 {
  16         paginating = true;
  17         paginate_skipping = false;
  18         paginate_pos = 0;
  19 }
  20 
  21 void xmon_end_pagination(void)
  22 {
  23         paginating = false;
  24 }
  25 
  26 void xmon_set_pagination_lpp(unsigned long lpp)
  27 {
  28         paginate_lpp = lpp;
  29 }
  30 
  31 static int xmon_readchar(void)
  32 {
  33         if (udbg_getc)
  34                 return udbg_getc();
  35         return -1;
  36 }
  37 
  38 static int xmon_write(const char *ptr, int nb)
  39 {
  40         int rv = 0;
  41         const char *p = ptr, *q;
  42         const char msg[] = "[Hit a key (a:all, q:truncate, any:next page)]";
  43 
  44         if (nb <= 0)
  45                 return rv;
  46 
  47         if (paginating && paginate_skipping)
  48                 return nb;
  49 
  50         if (paginate_lpp) {
  51                 while (paginating && (q = strchr(p, '\n'))) {
  52                         rv += udbg_write(p, q - p + 1);
  53                         p = q + 1;
  54                         paginate_pos++;
  55 
  56                         if (paginate_pos >= paginate_lpp) {
  57                                 udbg_write(msg, strlen(msg));
  58 
  59                                 switch (xmon_readchar()) {
  60                                 case 'a':
  61                                         paginating = false;
  62                                         break;
  63                                 case 'q':
  64                                         paginate_skipping = true;
  65                                         break;
  66                                 default:
  67                                         /* nothing */
  68                                         break;
  69                                 }
  70 
  71                                 paginate_pos = 0;
  72                                 udbg_write("\r\n", 2);
  73 
  74                                 if (paginate_skipping)
  75                                         return nb;
  76                         }
  77                 }
  78         }
  79 
  80         return rv + udbg_write(p, nb - (p - ptr));
  81 }
  82 
  83 int xmon_putchar(int c)
  84 {
  85         char ch = c;
  86 
  87         if (c == '\n')
  88                 xmon_putchar('\r');
  89         return xmon_write(&ch, 1) == 1? c: -1;
  90 }
  91 
  92 static char line[256];
  93 static char *lineptr;
  94 static int lineleft;
  95 
  96 static int xmon_getchar(void)
  97 {
  98         int c;
  99 
 100         if (lineleft == 0) {
 101                 lineptr = line;
 102                 for (;;) {
 103                         c = xmon_readchar();
 104                         if (c == -1 || c == 4)
 105                                 break;
 106                         if (c == '\r' || c == '\n') {
 107                                 *lineptr++ = '\n';
 108                                 xmon_putchar('\n');
 109                                 break;
 110                         }
 111                         switch (c) {
 112                         case 0177:
 113                         case '\b':
 114                                 if (lineptr > line) {
 115                                         xmon_putchar('\b');
 116                                         xmon_putchar(' ');
 117                                         xmon_putchar('\b');
 118                                         --lineptr;
 119                                 }
 120                                 break;
 121                         case 'U' & 0x1F:
 122                                 while (lineptr > line) {
 123                                         xmon_putchar('\b');
 124                                         xmon_putchar(' ');
 125                                         xmon_putchar('\b');
 126                                         --lineptr;
 127                                 }
 128                                 break;
 129                         default:
 130                                 if (lineptr >= &line[sizeof(line) - 1])
 131                                         xmon_putchar('\a');
 132                                 else {
 133                                         xmon_putchar(c);
 134                                         *lineptr++ = c;
 135                                 }
 136                         }
 137                 }
 138                 lineleft = lineptr - line;
 139                 lineptr = line;
 140         }
 141         if (lineleft == 0)
 142                 return -1;
 143         --lineleft;
 144         return *lineptr++;
 145 }
 146 
 147 char *xmon_gets(char *str, int nb)
 148 {
 149         char *p;
 150         int c;
 151 
 152         for (p = str; p < str + nb - 1; ) {
 153                 c = xmon_getchar();
 154                 if (c == -1) {
 155                         if (p == str)
 156                                 return NULL;
 157                         break;
 158                 }
 159                 *p++ = c;
 160                 if (c == '\n')
 161                         break;
 162         }
 163         *p = 0;
 164         return str;
 165 }
 166 
 167 void xmon_printf(const char *format, ...)
 168 {
 169         va_list args;
 170         static char xmon_outbuf[1024];
 171         int rc, n;
 172 
 173         va_start(args, format);
 174         n = vsnprintf(xmon_outbuf, sizeof(xmon_outbuf), format, args);
 175         va_end(args);
 176 
 177         rc = xmon_write(xmon_outbuf, n);
 178 
 179         if (n && rc == 0) {
 180                 /* No udbg hooks, fallback to printk() - dangerous */
 181                 printk("%s", xmon_outbuf);
 182         }
 183 }
 184 
 185 void xmon_puts(const char *str)
 186 {
 187         xmon_write(str, strlen(str));
 188 }

/* [<][>][^][v][top][bottom][index][help] */