4 Interface for perl stdio functions
8 #include "ipstdiowin.h"
11 class CPerlStdIO : public IPerlStdIOWin
20 virtual PerlIO* Stdin(void);
21 virtual PerlIO* Stdout(void);
22 virtual PerlIO* Stderr(void);
23 virtual PerlIO* Open(const char *, const char *, int &err);
24 virtual int Close(PerlIO*, int &err);
25 virtual int Eof(PerlIO*, int &err);
26 virtual int Error(PerlIO*, int &err);
27 virtual void Clearerr(PerlIO*, int &err);
28 virtual int Getc(PerlIO*, int &err);
29 virtual char* GetBase(PerlIO *, int &err);
30 virtual int GetBufsiz(PerlIO *, int &err);
31 virtual int GetCnt(PerlIO *, int &err);
32 virtual char* GetPtr(PerlIO *, int &err);
33 virtual int Putc(PerlIO*, int, int &err);
34 virtual int Puts(PerlIO*, const char *, int &err);
35 virtual int Flush(PerlIO*, int &err);
36 virtual int Ungetc(PerlIO*,int, int &err);
37 virtual int Fileno(PerlIO*, int &err);
38 virtual PerlIO* Fdopen(int, const char *, int &err);
39 virtual SSize_t Read(PerlIO*,void *,Size_t, int &err);
40 virtual SSize_t Write(PerlIO*,const void *,Size_t, int &err);
41 virtual void SetCnt(PerlIO *, int, int &err);
42 virtual void SetPtrCnt(PerlIO *, char *, int, int& err);
43 virtual void Setlinebuf(PerlIO*, int &err);
44 virtual int Printf(PerlIO*, int &err, const char *,...);
45 virtual int Vprintf(PerlIO*, int &err, const char *, va_list);
46 virtual long Tell(PerlIO*, int &err);
47 virtual int Seek(PerlIO*, off_t, int, int &err);
48 virtual void Rewind(PerlIO*, int &err);
49 virtual PerlIO* Tmpfile(int &err);
50 virtual int Getpos(PerlIO*, Fpos_t *, int &err);
51 virtual int Setpos(PerlIO*, const Fpos_t *, int &err);
52 virtual void Init(int &err);
53 virtual void InitOSExtras(void* p);
54 virtual int OpenOSfhandle(long osfhandle, int flags);
55 virtual int GetOSfhandle(int filenum);
59 inline void SetPerlObj(CPerlObj *p) { pPerl = p; };
60 inline void SetSockCtl(CPerlSock *p) { pSock = p; };
62 inline int IsWin95(void)
64 return (os_id() == VER_PLATFORM_WIN32_WINDOWS);
66 inline int IsWinNT(void)
68 return (os_id() == VER_PLATFORM_WIN32_NT);
70 inline void AddToSocketTable(int fh)
73 bSocketTable[fh] = TRUE;
75 inline BOOL InSocketTable(int fh)
78 return bSocketTable[fh];
81 inline void RemoveFromSocketTable(int fh)
84 bSocketTable[fh] = FALSE;
88 if((-1) == w32_platform)
92 memset(&osver, 0, sizeof(OSVERSIONINFO));
93 osver.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
95 w32_platform = osver.dwPlatformId;
97 return (w32_platform);
104 BOOL bSocketTable[_NSTREAM_];
107 void CPerlStdIO::ShutDown(void)
110 for(i = 0; i < _NSTREAM_; ++i)
113 pSock->CloseSocket(i, err);
118 extern "C" int __cdecl _alloc_osfhnd(void);
119 extern "C" int __cdecl _set_osfhnd(int fh, long value);
120 extern "C" void __cdecl _unlock(int);
122 #if (_MSC_VER >= 1000)
125 long osfhnd; /* underlying OS file HANDLE */
126 char osfile; /* attributes of file (e.g., open in text mode?) */
127 char pipech; /* one char buffer for handles opened on pipes */
129 extern "C" ioinfo * __pioinfo[];
131 #define IOINFO_ARRAY_ELTS (1 << IOINFO_L2E)
132 #define _pioinfo(i) (__pioinfo[i >> IOINFO_L2E] + (i & (IOINFO_ARRAY_ELTS - 1)))
133 #define _osfile(i) (_pioinfo(i)->osfile)
135 extern "C" extern char _osfile[];
136 #endif // (_MSC_VER >= 1000)
138 #define FOPEN 0x01 // file handle open
139 #define FAPPEND 0x20 // file handle opened O_APPEND
140 #define FDEV 0x40 // file handle refers to device
141 #define FTEXT 0x80 // file handle is in text mode
143 #define _STREAM_LOCKS 26 // Table of stream locks
144 #define _LAST_STREAM_LOCK (_STREAM_LOCKS+_NSTREAM_-1) // Last stream lock
145 #define _FH_LOCKS (_LAST_STREAM_LOCK+1) // Table of fh locks
148 int CPerlStdIO::OpenOSfhandle(long osfhandle, int flags)
155 // all this is here to handle Win95's GetFileType bug.
156 char fileflags; // _osfile flags
158 // copy relevant flags from second parameter
161 if(flags & _O_APPEND)
162 fileflags |= FAPPEND;
167 // attempt to allocate a C Runtime file handle
168 if((fh = _alloc_osfhnd()) == -1)
170 errno = EMFILE; // too many open files
171 _doserrno = 0L; // not an OS error
172 return -1; // return error to caller
175 // the file is open. now, set the info in _osfhnd array
176 _set_osfhnd(fh, osfhandle);
178 fileflags |= FOPEN; // mark as open
180 #if (_MSC_VER >= 1000)
181 _osfile(fh) = fileflags; // set osfile entry
183 _osfile[fh] = fileflags; // set osfile entry
188 fh = _open_osfhandle(osfhandle, flags);
191 AddToSocketTable(fh);
193 return fh; // return handle
196 int CPerlStdIO::GetOSfhandle(int filenum)
198 return _get_osfhandle(filenum);
201 PerlIO* CPerlStdIO::Stdin(void)
203 return (PerlIO*)(&_iob[0]);
206 PerlIO* CPerlStdIO::Stdout(void)
208 return (PerlIO*)(&_iob[1]);
211 PerlIO* CPerlStdIO::Stderr(void)
213 return (PerlIO*)(&_iob[2]);
216 PerlIO* CPerlStdIO::Open(const char *path, const char *mode, int &err)
221 ret = (PerlIO*)fopen(path, mode);
230 extern "C" int _free_osfhnd(int fh);
231 int CPerlStdIO::Close(PerlIO* pf, int &err)
233 int ret = 0, fileNo = fileno((FILE*)pf);
234 if(InSocketTable(fileNo))
236 RemoveFromSocketTable(fileNo);
237 pSock->CloseSocket(fileNo, err);
238 _free_osfhnd(fileNo);
242 ret = fclose((FILE*)pf);
249 int CPerlStdIO::Eof(PerlIO* pf, int &err)
251 int ret = feof((FILE*)pf);
257 int CPerlStdIO::Error(PerlIO* pf, int &err)
259 int ret = ferror((FILE*)pf);
265 void CPerlStdIO::Clearerr(PerlIO* pf, int &err)
271 int CPerlStdIO::Getc(PerlIO* pf, int &err)
273 int ret = fgetc((FILE*)pf);
279 int CPerlStdIO::Putc(PerlIO* pf, int c, int &err)
281 int ret = fputc(c, (FILE*)pf);
287 int CPerlStdIO::Puts(PerlIO* pf, const char *s, int &err)
289 int ret = fputs(s, (FILE*)pf);
295 int CPerlStdIO::Flush(PerlIO* pf, int &err)
297 int ret = fflush((FILE*)pf);
303 int CPerlStdIO::Ungetc(PerlIO* pf,int c, int &err)
305 int ret = ungetc(c, (FILE*)pf);
311 int CPerlStdIO::Fileno(PerlIO* pf, int &err)
313 int ret = fileno((FILE*)pf);
319 PerlIO* CPerlStdIO::Fdopen(int fh, const char *mode, int &err)
321 PerlIO* ret = (PerlIO*)fdopen(fh, mode);
327 SSize_t CPerlStdIO::Read(PerlIO* pf, void * buffer, Size_t count, int &err)
329 size_t ret = fread(buffer, 1, count, (FILE*)pf);
335 SSize_t CPerlStdIO::Write(PerlIO* pf, const void * buffer, Size_t count, int &err)
337 size_t ret = fwrite(buffer, 1, count, (FILE*)pf);
343 void CPerlStdIO::Setlinebuf(PerlIO*, int &err)
345 croak("setlinebuf not implemented!\n");
348 int CPerlStdIO::Printf(PerlIO* pf, int &err, const char *format, ...)
351 va_start(arglist, format);
352 int ret = Vprintf(pf, err, format, arglist);
358 int CPerlStdIO::Vprintf(PerlIO* pf, int &err, const char * format, va_list arg)
360 int ret = vfprintf((FILE*)pf, format, arg);
366 long CPerlStdIO::Tell(PerlIO* pf, int &err)
368 long ret = ftell((FILE*)pf);
374 int CPerlStdIO::Seek(PerlIO* pf, off_t offset, int origin, int &err)
376 int ret = fseek((FILE*)pf, offset, origin);
382 void CPerlStdIO::Rewind(PerlIO* pf, int &err)
387 PerlIO* CPerlStdIO::Tmpfile(int &err)
389 return (PerlIO*)tmpfile();
392 int CPerlStdIO::Getpos(PerlIO* pf, Fpos_t *p, int &err)
394 int ret = fgetpos((FILE*)pf, (fpos_t*)p);
400 int CPerlStdIO::Setpos(PerlIO* pf, const Fpos_t *p, int &err)
402 int ret = fsetpos((FILE*)pf, (fpos_t*)p);
408 char* CPerlStdIO::GetBase(PerlIO *pf, int &err)
410 return ((FILE*)pf)->_base;
413 int CPerlStdIO::GetBufsiz(PerlIO *pf, int &err)
415 return ((FILE*)pf)->_bufsiz;
418 int CPerlStdIO::GetCnt(PerlIO *pf, int &err)
420 return ((FILE*)pf)->_cnt;
423 char* CPerlStdIO::GetPtr(PerlIO *pf, int &err)
425 return ((FILE*)pf)->_ptr;
428 void CPerlStdIO::SetCnt(PerlIO *pf, int n, int &err)
430 ((FILE*)pf)->_cnt = n;
433 void CPerlStdIO::SetPtrCnt(PerlIO *pf, char *ptr, int n, int& err)
435 ((FILE*)pf)->_ptr = ptr;
436 ((FILE*)pf)->_cnt = n;
439 void CPerlStdIO::Init(int &err)
443 void CPerlStdIO::InitOSExtras(void* p)