@@ -1127,15 +1127,61 @@ static int aio_cmd_copy(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
11271127 return JIM_OK ;
11281128}
11291129
1130+ /* Like strstr() but optimised in the case the the needle is of length 1 */
1131+ static const char * jim_strstr (const char * haystack , int haylen , const char * needle , int needlen )
1132+ {
1133+ if (needlen == 1 ) {
1134+ return (const char * )memchr (haystack , needle [0 ], strlen (haystack ));
1135+ }
1136+ return strstr (haystack , needle );
1137+ }
1138+
11301139static int aio_cmd_gets (Jim_Interp * interp , int argc , Jim_Obj * const * argv )
11311140{
11321141 AioFile * af = Jim_CmdPrivData (interp );
11331142 Jim_Obj * objPtr = NULL ;
11341143 int len ;
11351144 int nb ;
11361145 unsigned flags = AIO_ONEREAD ;
1137- char * nl = NULL ;
1146+ const char * nl = NULL ;
11381147 int offset = 0 ;
1148+ long keepnl = 0 ;
1149+ const char * nlstr = "\n" ;
1150+ int nlstrlen = 1 ;
1151+
1152+ while (argc >= 2 ) {
1153+ enum {OPT_EOL , OPT_KEEP };
1154+ static const char * const options [] = {
1155+ "-eol" ,
1156+ "-keep" ,
1157+ NULL
1158+ };
1159+ int opt ;
1160+
1161+ if (Jim_GetEnum (interp , argv [0 ], options , & opt , NULL , JIM_ERRMSG | JIM_ENUM_ABBREV ) != JIM_OK ) {
1162+ return JIM_ERR ;
1163+ }
1164+
1165+ switch (opt ) {
1166+ case OPT_EOL :
1167+ nlstr = Jim_GetString (argv [1 ], & nlstrlen );
1168+ break ;
1169+
1170+ case OPT_KEEP :
1171+ if (Jim_GetLong (interp , argv [1 ], & keepnl ) != JIM_OK ) {
1172+ return JIM_ERR ;
1173+ }
1174+ break ;
1175+ default :
1176+ return JIM_ERR ;
1177+ }
1178+ argc -= 2 ;
1179+ argv += 2 ;
1180+ }
1181+
1182+ if (argc > 1 ) {
1183+ return JIM_USAGE ;
1184+ }
11391185
11401186 errno = 0 ;
11411187
@@ -1148,10 +1194,10 @@ static int aio_cmd_gets(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
11481194 while (!aio_eof (af )) {
11491195 if (af -> readbuf ) {
11501196 const char * pt = Jim_GetString (af -> readbuf , & len );
1151- nl = memchr (pt + offset , '\n' , len - offset );
1197+ nl = jim_strstr (pt + offset , len - offset , nlstr , nlstrlen );
11521198 if (nl ) {
11531199 /* got a line */
1154- objPtr = Jim_NewStringObj (interp , pt , nl - pt );
1200+ objPtr = Jim_NewStringObj (interp , pt , nl - pt + ( keepnl ? nlstrlen : 0 ) );
11551201 /* And consume it plus the newline */
11561202 aio_consume (af -> readbuf , nl - pt + 1 );
11571203 break ;
@@ -2169,10 +2215,10 @@ static const jim_subcmd_type aio_command_table[] = {
21692215 /* Description: Internal command to return the taint of the channel. */
21702216 },
21712217 { "gets" ,
2172- "?var?" ,
2218+ "?-eol <str>? ?-keep 0|1? ? var?" ,
21732219 aio_cmd_gets ,
21742220 0 ,
2175- 1 ,
2221+ - 1 ,
21762222 /* Description: Read one line and return it or store it in the var */
21772223 },
21782224 { "puts" ,
0 commit comments