mirror of
https://github.com/libretro/RetroArch
synced 2025-03-23 19:21:03 +00:00
(libretro-common) Create stdin_stream.c
This commit is contained in:
parent
4ed3e750d4
commit
58787e6d89
@ -172,6 +172,7 @@ OBJ += frontend/frontend.o \
|
||||
$(LIBRETRO_COMM_DIR)/lists/file_list.o \
|
||||
$(LIBRETRO_COMM_DIR)/lists/dir_list.o \
|
||||
$(LIBRETRO_COMM_DIR)/file/retro_dirent.o \
|
||||
$(LIBRETRO_COMM_DIR)/streams/stdin_stream.o \
|
||||
$(LIBRETRO_COMM_DIR)/streams/file_stream.o \
|
||||
$(LIBRETRO_COMM_DIR)/streams/interface_stream.o \
|
||||
$(LIBRETRO_COMM_DIR)/streams/memory_stream.o \
|
||||
|
121
command.c
121
command.c
@ -18,27 +18,22 @@
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
|
||||
#ifdef _WIN32
|
||||
#include <direct.h>
|
||||
#else
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
|
||||
#include <compat/strl.h>
|
||||
#include <compat/posix_string.h>
|
||||
#include <file/file_path.h>
|
||||
#include <lists/dir_list.h>
|
||||
#include <string/stdstring.h>
|
||||
#include <streams/stdin_stream.h>
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_COMMAND
|
||||
#ifdef HAVE_NETWORKING
|
||||
#include <net/net_compat.h>
|
||||
#include <net/net_socket.h>
|
||||
#endif
|
||||
#ifdef HAVE_NETWORKING
|
||||
#include <net/net_compat.h>
|
||||
#include <net/net_socket.h>
|
||||
#endif
|
||||
#include <string/stdstring.h>
|
||||
#endif
|
||||
|
||||
@ -589,112 +584,6 @@ error:
|
||||
|
||||
#ifdef HAVE_STDIN_CMD
|
||||
|
||||
#ifdef _WIN32
|
||||
static size_t read_stdin(char *buf, size_t size)
|
||||
{
|
||||
DWORD i;
|
||||
DWORD has_read = 0;
|
||||
DWORD avail = 0;
|
||||
bool echo = false;
|
||||
HANDLE hnd = GetStdHandle(STD_INPUT_HANDLE);
|
||||
|
||||
if (hnd == INVALID_HANDLE_VALUE)
|
||||
return 0;
|
||||
|
||||
/* Check first if we're a pipe
|
||||
* (not console). */
|
||||
|
||||
/* If not a pipe, check if we're running in a console. */
|
||||
if (!PeekNamedPipe(hnd, NULL, 0, NULL, &avail, NULL))
|
||||
{
|
||||
INPUT_RECORD recs[256];
|
||||
bool has_key = false;
|
||||
DWORD mode = 0;
|
||||
DWORD has_read = 0;
|
||||
|
||||
if (!GetConsoleMode(hnd, &mode))
|
||||
return 0;
|
||||
|
||||
if ((mode & (ENABLE_LINE_INPUT | ENABLE_ECHO_INPUT))
|
||||
&& !SetConsoleMode(hnd,
|
||||
mode & ~(ENABLE_LINE_INPUT | ENABLE_ECHO_INPUT)))
|
||||
return 0;
|
||||
|
||||
/* Win32, Y U NO SANE NONBLOCK READ!? */
|
||||
if (!PeekConsoleInput(hnd, recs,
|
||||
sizeof(recs) / sizeof(recs[0]), &has_read))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < has_read; i++)
|
||||
{
|
||||
/* Very crude, but should get the job done. */
|
||||
if (recs[i].EventType == KEY_EVENT &&
|
||||
recs[i].Event.KeyEvent.bKeyDown &&
|
||||
(isgraph(recs[i].Event.KeyEvent.wVirtualKeyCode) ||
|
||||
recs[i].Event.KeyEvent.wVirtualKeyCode == VK_RETURN))
|
||||
{
|
||||
has_key = true;
|
||||
echo = true;
|
||||
avail = size;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!has_key)
|
||||
{
|
||||
FlushConsoleInputBuffer(hnd);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (!avail)
|
||||
return 0;
|
||||
|
||||
if (avail > size)
|
||||
avail = size;
|
||||
|
||||
if (!ReadFile(hnd, buf, avail, &has_read, NULL))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < has_read; i++)
|
||||
if (buf[i] == '\r')
|
||||
buf[i] = '\n';
|
||||
|
||||
/* Console won't echo for us while in non-line mode,
|
||||
* so do it manually ... */
|
||||
if (echo)
|
||||
{
|
||||
HANDLE hnd_out = GetStdHandle(STD_OUTPUT_HANDLE);
|
||||
if (hnd_out != INVALID_HANDLE_VALUE)
|
||||
{
|
||||
DWORD has_written;
|
||||
WriteConsole(hnd_out, buf, has_read, &has_written, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
return has_read;
|
||||
}
|
||||
#else
|
||||
|
||||
static size_t read_stdin(char *buf, size_t size)
|
||||
{
|
||||
size_t has_read = 0;
|
||||
|
||||
while (size)
|
||||
{
|
||||
ssize_t ret = read(STDIN_FILENO, buf, size);
|
||||
|
||||
if (ret <= 0)
|
||||
break;
|
||||
|
||||
buf += ret;
|
||||
has_read += ret;
|
||||
size -= ret;
|
||||
}
|
||||
|
||||
return has_read;
|
||||
}
|
||||
#endif
|
||||
|
||||
static void command_stdin_poll(command_t *handle)
|
||||
{
|
||||
|
@ -65,6 +65,7 @@ ARCHIVE FILE
|
||||
/*============================================================
|
||||
COMPRESSION
|
||||
============================================================ */
|
||||
#include "../libretro-common/streams/stdin_stream.c"
|
||||
#include "../libretro-common/streams/trans_stream.c"
|
||||
#include "../libretro-common/streams/trans_stream_pipe.c"
|
||||
|
||||
|
40
libretro-common/include/streams/stdin_stream.h
Normal file
40
libretro-common/include/streams/stdin_stream.h
Normal file
@ -0,0 +1,40 @@
|
||||
/* Copyright (C) 2010-2017 The RetroArch team
|
||||
*
|
||||
* ---------------------------------------------------------------------------------------
|
||||
* The following license statement only applies to this file (stdin_stream.h).
|
||||
* ---------------------------------------------------------------------------------------
|
||||
*
|
||||
* Permission is hereby granted, free of charge,
|
||||
* to any person obtaining a copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation the rights to
|
||||
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software,
|
||||
* and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
|
||||
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
*/
|
||||
|
||||
#ifndef LIBRETRO_SDK_STDIN_STREAM_H__
|
||||
#define LIBRETRO_SDK_STDIN_STREAM_H__
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stddef.h>
|
||||
|
||||
#include <retro_miscellaneous.h>
|
||||
|
||||
#include <retro_common_api.h>
|
||||
|
||||
RETRO_BEGIN_DECLS
|
||||
|
||||
size_t read_stdin(char *buf, size_t size);
|
||||
|
||||
RETRO_END_DECLS
|
||||
|
||||
#endif
|
||||
|
136
libretro-common/streams/stdin_stream.c
Normal file
136
libretro-common/streams/stdin_stream.c
Normal file
@ -0,0 +1,136 @@
|
||||
/* Copyright (C) 2010-2017 The RetroArch team
|
||||
*
|
||||
* ---------------------------------------------------------------------------------------
|
||||
* The following license statement only applies to this file (stdin_stream.c).
|
||||
* ---------------------------------------------------------------------------------------
|
||||
*
|
||||
* Permission is hereby granted, free of charge,
|
||||
* to any person obtaining a copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation the rights to
|
||||
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software,
|
||||
* and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
|
||||
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
|
||||
#ifdef _WIN32
|
||||
#include <direct.h>
|
||||
#else
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
size_t read_stdin(char *buf, size_t size)
|
||||
{
|
||||
DWORD i;
|
||||
DWORD has_read = 0;
|
||||
DWORD avail = 0;
|
||||
bool echo = false;
|
||||
HANDLE hnd = GetStdHandle(STD_INPUT_HANDLE);
|
||||
|
||||
if (hnd == INVALID_HANDLE_VALUE)
|
||||
return 0;
|
||||
|
||||
/* Check first if we're a pipe
|
||||
* (not console). */
|
||||
|
||||
/* If not a pipe, check if we're running in a console. */
|
||||
if (!PeekNamedPipe(hnd, NULL, 0, NULL, &avail, NULL))
|
||||
{
|
||||
INPUT_RECORD recs[256];
|
||||
bool has_key = false;
|
||||
DWORD mode = 0;
|
||||
DWORD has_read = 0;
|
||||
|
||||
if (!GetConsoleMode(hnd, &mode))
|
||||
return 0;
|
||||
|
||||
if ((mode & (ENABLE_LINE_INPUT | ENABLE_ECHO_INPUT))
|
||||
&& !SetConsoleMode(hnd,
|
||||
mode & ~(ENABLE_LINE_INPUT | ENABLE_ECHO_INPUT)))
|
||||
return 0;
|
||||
|
||||
/* Win32, Y U NO SANE NONBLOCK READ!? */
|
||||
if (!PeekConsoleInput(hnd, recs,
|
||||
sizeof(recs) / sizeof(recs[0]), &has_read))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < has_read; i++)
|
||||
{
|
||||
/* Very crude, but should get the job done. */
|
||||
if (recs[i].EventType == KEY_EVENT &&
|
||||
recs[i].Event.KeyEvent.bKeyDown &&
|
||||
(isgraph(recs[i].Event.KeyEvent.wVirtualKeyCode) ||
|
||||
recs[i].Event.KeyEvent.wVirtualKeyCode == VK_RETURN))
|
||||
{
|
||||
has_key = true;
|
||||
echo = true;
|
||||
avail = size;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!has_key)
|
||||
{
|
||||
FlushConsoleInputBuffer(hnd);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (!avail)
|
||||
return 0;
|
||||
|
||||
if (avail > size)
|
||||
avail = size;
|
||||
|
||||
if (!ReadFile(hnd, buf, avail, &has_read, NULL))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < has_read; i++)
|
||||
if (buf[i] == '\r')
|
||||
buf[i] = '\n';
|
||||
|
||||
/* Console won't echo for us while in non-line mode,
|
||||
* so do it manually ... */
|
||||
if (echo)
|
||||
{
|
||||
HANDLE hnd_out = GetStdHandle(STD_OUTPUT_HANDLE);
|
||||
if (hnd_out != INVALID_HANDLE_VALUE)
|
||||
{
|
||||
DWORD has_written;
|
||||
WriteConsole(hnd_out, buf, has_read, &has_written, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
return has_read;
|
||||
}
|
||||
#else
|
||||
size_t read_stdin(char *buf, size_t size)
|
||||
{
|
||||
size_t has_read = 0;
|
||||
|
||||
while (size)
|
||||
{
|
||||
ssize_t ret = read(STDIN_FILENO, buf, size);
|
||||
|
||||
if (ret <= 0)
|
||||
break;
|
||||
|
||||
buf += ret;
|
||||
has_read += ret;
|
||||
size -= ret;
|
||||
}
|
||||
|
||||
return has_read;
|
||||
}
|
||||
#endif
|
Loading…
x
Reference in New Issue
Block a user