mirror of
https://github.com/unicode-org/icu.git
synced 2025-04-07 06:25:30 +00:00
ICU-3720 Make it possible to read from stdin.
Can't easily automate this test case X-SVN-Rev: 16153
This commit is contained in:
parent
2cb0f10a47
commit
c6099fb59d
4 changed files with 63 additions and 21 deletions
|
@ -27,6 +27,10 @@
|
|||
#include "cstring.h"
|
||||
#include "cmemory.h"
|
||||
|
||||
#ifdef WIN32
|
||||
/* Windows likes to rename Unix-like functions */
|
||||
#define fileno _fileno
|
||||
#endif
|
||||
|
||||
U_CAPI UFILE* U_EXPORT2 /* U_CAPI ... U_EXPORT2 added by Peter Kirk 17 Nov 2001 */
|
||||
u_finit(FILE *f,
|
||||
|
@ -40,21 +44,18 @@ u_finit(FILE *f,
|
|||
}
|
||||
|
||||
uprv_memset(result, 0, sizeof(UFILE));
|
||||
result->fFileno = fileno(f);
|
||||
|
||||
#ifdef WIN32
|
||||
{
|
||||
int filenum = _fileno(f);
|
||||
if (0 <= filenum && filenum <= 2) {
|
||||
/* stdin, stdout and stderr need to be special cased for Windows 98 */
|
||||
result->fFile = &_iob[_fileno(f)];
|
||||
}
|
||||
else {
|
||||
result->fFile = f;
|
||||
}
|
||||
if (0 <= result->fFileno && result->fFileno <= 2) {
|
||||
/* stdin, stdout and stderr need to be special cased for Windows 98 */
|
||||
result->fFile = &_iob[_fileno(f)];
|
||||
}
|
||||
#else
|
||||
result->fFile = f;
|
||||
else
|
||||
#endif
|
||||
{
|
||||
result->fFile = f;
|
||||
}
|
||||
|
||||
result->str.fBuffer = result->fUCBuffer;
|
||||
result->str.fPos = result->fUCBuffer;
|
||||
|
|
|
@ -68,6 +68,8 @@ struct UFILE {
|
|||
UChar fUCBuffer[UFILE_UCHARBUFFER_SIZE];/* buffer used for toUnicode */
|
||||
|
||||
UBool fOwnFile; /* TRUE if fFile should be closed */
|
||||
|
||||
int32_t fFileno; /* File number. Useful to determine if it's stdin. */
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
@ -20,6 +20,7 @@
|
|||
#include "unicode/ustdio.h"
|
||||
#include "unicode/putil.h"
|
||||
#include "cmemory.h"
|
||||
#include "cstring.h"
|
||||
#include "ufile.h"
|
||||
#include "ufmt_cmn.h"
|
||||
#include "unicode/ucnv.h"
|
||||
|
@ -396,13 +397,16 @@ ufile_fill_uchar_buffer(UFILE *f)
|
|||
return;
|
||||
}
|
||||
|
||||
/* shift the buffer if it isn't empty */
|
||||
str = &f->str;
|
||||
dataSize = (int32_t)(str->fLimit - str->fPos);
|
||||
if (f->fFileno == 0 && dataSize > 0) {
|
||||
/* Don't read from stdin too many times. There is still some data. */
|
||||
return;
|
||||
}
|
||||
|
||||
/* shift the buffer if it isn't empty */
|
||||
if(dataSize != 0) {
|
||||
memmove(f->fUCBuffer,
|
||||
str->fPos,
|
||||
dataSize * sizeof(UChar));
|
||||
uprv_memmove(f->fUCBuffer, str->fPos, dataSize * sizeof(UChar));
|
||||
}
|
||||
|
||||
|
||||
|
@ -414,10 +418,18 @@ ufile_fill_uchar_buffer(UFILE *f)
|
|||
maxCPBytes = availLength / (f->fConverter!=NULL?(2*ucnv_getMinCharSize(f->fConverter)):1);
|
||||
|
||||
/* Read in the data to convert */
|
||||
bytesRead = (int32_t)fread(charBuffer,
|
||||
sizeof(char),
|
||||
ufmt_min(maxCPBytes, UFILE_CHARBUFFER_SIZE),
|
||||
f->fFile);
|
||||
if (f->fFileno == 0) {
|
||||
/* Special case. Read from stdin one line at a time. */
|
||||
char *retStr = fgets(charBuffer, ufmt_min(maxCPBytes, UFILE_CHARBUFFER_SIZE), f->fFile);
|
||||
bytesRead = (retStr ? uprv_strlen(charBuffer) : 0);
|
||||
}
|
||||
else {
|
||||
/* A normal file */
|
||||
bytesRead = (int32_t)fread(charBuffer,
|
||||
sizeof(char),
|
||||
ufmt_min(maxCPBytes, UFILE_CHARBUFFER_SIZE),
|
||||
f->fFile);
|
||||
}
|
||||
|
||||
/* Set up conversion parameters */
|
||||
status = U_ZERO_ERROR;
|
||||
|
@ -555,7 +567,9 @@ ufile_getch(UFILE *f, UChar *ch)
|
|||
}
|
||||
else if (f) {
|
||||
/* otherwise, fill the buffer and return the next character */
|
||||
ufile_fill_uchar_buffer(f);
|
||||
if(f->str.fPos >= f->str.fLimit) {
|
||||
ufile_fill_uchar_buffer(f);
|
||||
}
|
||||
if(f->str.fPos < f->str.fLimit) {
|
||||
*ch = *(f->str.fPos)++;
|
||||
isValidChar = TRUE;
|
||||
|
|
|
@ -23,8 +23,8 @@
|
|||
const char STANDARD_TEST_FILE[] = "iotest-c.txt";
|
||||
|
||||
|
||||
static void TestFileFromICU(UFILE *myFile) {
|
||||
#if !UCONFIG_NO_FORMATTING
|
||||
static void TestFileFromICU(UFILE *myFile) {
|
||||
int32_t n[1];
|
||||
float myFloat = -1234.0;
|
||||
int32_t newValuePtr[1];
|
||||
|
@ -317,6 +317,30 @@ static void TestFile(void) {
|
|||
TestFileFromICU(u_finit(standardFile, NULL, NULL));
|
||||
fclose(standardFile);
|
||||
*/
|
||||
}
|
||||
#endif
|
||||
|
||||
static void StdinBuffering(void) {
|
||||
#if 0
|
||||
UChar buff[255];
|
||||
int32_t num = 0;
|
||||
UFILE *uStdIn = NULL;
|
||||
UFILE *uStdOut = NULL;
|
||||
uStdIn = u_finit(stdin, NULL, NULL);
|
||||
uStdOut = u_finit(stdout, NULL, NULL);
|
||||
if (uStdIn == NULL)
|
||||
return;
|
||||
|
||||
buff[0] = 0x40;
|
||||
buff[1] = 0;
|
||||
u_fgets(buff, sizeof(buff)/sizeof(buff[0]), uStdIn);
|
||||
u_fprintf(uStdOut, "%S\n", buff);
|
||||
u_fscanf(uStdIn, "%d", &num);
|
||||
u_fprintf(uStdOut, "%d\n", num);
|
||||
u_fscanf(uStdIn, "%d", &num);
|
||||
u_fprintf(uStdOut, "%d\n", num);
|
||||
#else
|
||||
log_verbose("Test disabled because it requires user interaction");
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@ -1415,6 +1439,7 @@ addFileTest(TestNode** root) {
|
|||
#if !UCONFIG_NO_FORMATTING
|
||||
addTest(root, &TestFile, "file/TestFile");
|
||||
#endif
|
||||
addTest(root, &StdinBuffering, "file/StdinBuffering");
|
||||
addTest(root, &TestfgetsBuffers, "file/TestfgetsBuffers");
|
||||
addTest(root, &TestfgetsLineCount, "file/TestfgetsLineCount");
|
||||
addTest(root, &TestfgetsNewLineHandling, "file/TestfgetsNewLineHandling");
|
||||
|
|
Loading…
Add table
Reference in a new issue