io.c (3996B)
1 /* 2 * 3 * This license is set out in https://raw.githubusercontent.com/Broadcom-Network-Switching-Software/OpenBCM/master/Legal/LICENSE file. 4 * 5 * Copyright 2007-2019 Broadcom Inc. All rights reserved. 6 * 7 * SAL I/O abstraction 8 */ 9 10 #include <sal/core/libc.h> 11 #include <sal/core/alloc.h> 12 #include <sal/core/spl.h> 13 #include <sal/core/thread.h> 14 #include <sal/core/dpc.h> 15 16 #include <shared/bsl.h> 17 18 #include <sal/appl/io.h> 19 20 #include "sal/appl/editline/editline.h" 21 22 #include <stdarg.h> 23 24 #ifdef ECOS_LOGGING_SUPPORT 25 /* Logging mechanism for Mozart */ 26 #include <cyg/logging/logging.h> 27 #endif /* ECOS_LOGGING_SUPPORT */ 28 29 30 #ifndef SDK_CONFIG_SAL_READLINE 31 /* 32 * Read input line, providing Emacs-based command history editing. 33 */ 34 35 char * 36 sal_readline(char *prompt, char *buf, int bufsize, char *defl) 37 { 38 char *s, *full_prompt, *cont_prompt; 39 #ifdef INCLUDE_EDITLINE 40 extern void rl_prompt_set(CONST char *prompt); 41 #else 42 char *t; 43 #endif 44 int len; 45 46 if (bufsize == 0) 47 return NULL; 48 49 cont_prompt = prompt[0] ? "? " : ""; 50 full_prompt = sal_alloc(sal_strlen(prompt) + (defl ? sal_strlen(defl) : 0) + 8, __FILE__); 51 /* coverity[secure_coding] */ 52 sal_strcpy(full_prompt, prompt); 53 if (defl) 54 sal_sprintf(full_prompt + sal_strlen(full_prompt), "[%s] ", defl); 55 56 #ifdef INCLUDE_EDITLINE 57 58 LOG_INFO(BSL_LS_APPL_ECHO, 59 (BSL_META("%s"), full_prompt)); 60 s = readline(full_prompt); 61 62 #else /* !INCLUDE_EDITLINE */ 63 64 t = sal_alloc(bufsize, __FILE__); 65 #if defined(KEYSTONE) && defined(__ECOS) 66 diag_printf("%s", full_prompt); 67 #else 68 cli_out("%s", full_prompt); 69 #endif 70 71 if ((s = sal_console_gets(t, bufsize)) == 0) { 72 sal_free(t); 73 } else { 74 s[bufsize - 1] = 0; 75 if ((t = strchr(s, '\n')) != 0) { 76 *t = 0; 77 /* Replace garbage characters with spaces */ 78 } 79 for (t = s; *t; t++) { 80 if (*t < 32 && *t != 7 && *t != 9) { 81 *t = ' '; 82 } 83 } 84 } 85 86 #endif /* !INCLUDE_EDITLINE */ 87 88 if (s == 0) { /* Handle Control-D */ 89 buf[0] = 0; 90 /* EOF */ 91 buf = 0; 92 goto done; 93 } else { 94 LOG_INFO(BSL_LS_APPL_ECHO, 95 (BSL_META("%s\n"), s)); 96 } 97 98 len = 0; 99 if (s[0] == 0) { 100 if (defl && buf != defl) { 101 if ((len = sal_strlen(defl)) >= bufsize) { 102 len = bufsize - 1; 103 } 104 sal_memcpy(buf, defl, len); 105 } 106 } else { 107 if ((len = sal_strlen(s)) >= bufsize) { 108 len = bufsize - 1; 109 cli_out("WARNING: input line truncated to %d chars\n", len); 110 } 111 sal_memcpy(buf, s, len); 112 } 113 buf[len] = 0; 114 115 sal_free(s); 116 117 /* 118 * If line ends in a backslash, perform a continuation prompt. 119 */ 120 121 if (sal_strlen(buf) != 0) { 122 /* 123 * Ensure that there is atleast one character available 124 */ 125 s = buf + sal_strlen(buf) - 1; 126 if (*s == '\\' && sal_readline(cont_prompt, s, bufsize - (s - buf), 0) == 0) { 127 buf = 0; 128 } 129 } 130 131 done: 132 #ifdef INCLUDE_EDITLINE 133 rl_prompt_set(NULL); 134 #endif 135 sal_free(full_prompt); 136 137 return buf; 138 } 139 #endif /* !SDK_CONFIG_SAL_READLINE */ 140 141 int sal_readchar(const char *prompt) 142 { 143 #ifdef INCLUDE_EDITLINE 144 extern int readchar(const char *prompt); 145 #else 146 char buf[64]; 147 #endif 148 149 #ifdef INCLUDE_EDITLINE 150 return(readchar(prompt)); 151 #else 152 cli_out("%s", prompt); 153 if (NULL == (sal_console_gets(buf, sizeof(buf)))) { 154 return(EOF); 155 } else { 156 return(buf[0]); 157 } 158 #endif 159 } 160 161 #ifdef INCLUDE_EDITLINE 162 /* 163 * Configure readline by passing it completion routine (for TAB 164 * completion handling) and a list-possible routine (for ESC-? handling). 165 */ 166 167 void sal_readline_config(char *(*complete)(char *pathname, int *unique), 168 int (*list_possib)(char *pathname, char ***avp)) 169 { 170 extern char *(*rl_complete)(char *, int *); 171 extern int (*rl_list_possib)(char *, char ***); 172 173 rl_complete = complete; 174 rl_list_possib = list_possib; 175 } 176 #endif /* INCLUDE_EDITLINE */