2 * DEC 93 Erik Bos (erik@trashcan.hacktic.nl)
13 #include <sys/ioctl.h>
22 int commerror
= 0, eventmask
= 0;
24 struct DosDeviceStruct
{
25 char *devicename
; /* /dev/cua1 */
30 struct DosDeviceStruct COM
[MAX_PORTS
];
31 struct DosDeviceStruct LPT
[MAX_PORTS
];
33 void Comm_DeInit(void);
37 int x
, serial
= 0, parallel
= 0;
38 char option
[10], temp
[256], *ptr
;
41 for (x
=0; x
!=MAX_PORTS
; x
++) {
42 strcpy(option
,"COMx");
46 GetPrivateProfileString("serialports", option
, "*", temp
, sizeof(temp
), WINE_INI
);
47 if (!strcmp(temp
, "*") || *temp
== '\0')
48 COM
[serial
].devicename
= NULL
;
51 if (!S_ISCHR(st
.st_mode
))
52 fprintf(stderr
,"comm: can 't use `%s' as COM%d !\n", temp
, x
);
54 if ((ptr
= malloc(strlen(temp
)+1)) == NULL
)
55 fprintf(stderr
,"comm: can't malloc for device info!\n");
58 COM
[serial
].devicename
= ptr
;
59 strcpy(COM
[serial
++].devicename
, temp
);
63 strcpy(option
, "LPTx");
67 GetPrivateProfileString("parallelports", option
, "*", temp
, sizeof(temp
), WINE_INI
);
68 if (!strcmp(temp
, "*") || *temp
== '\0')
69 LPT
[parallel
].devicename
= NULL
;
72 if (!S_ISCHR(st
.st_mode
))
73 fprintf(stderr
,"comm: can 't use `%s' as LPT%d !\n", temp
, x
);
75 if ((ptr
= malloc(strlen(temp
)+1)) == NULL
)
76 fprintf(stderr
,"comm: can't malloc for device info!\n");
79 LPT
[serial
].devicename
= ptr
;
80 strcpy(LPT
[serial
++].devicename
, temp
);
88 for (x
=0; x
!=MAX_PORTS
; x
++) {
89 if (COM
[x
].devicename
)
90 fprintf(stderr
, "comm: COM%d = %s\n", x
, COM
[x
].devicename
);
91 if (LPT
[x
].devicename
)
92 fprintf(stderr
, "comm: LPT%d = %s\n", x
, LPT
[x
].devicename
);
97 void Comm_DeInit(void)
101 for (x
=0; x
!=MAX_PORTS
; x
++) {
103 if (COM
[x
].devicename
) {
106 fprintf(stderr
, "comm: COM%d = %s\n",x
,COM
[x
].devicename
);
107 free(COM
[x
].devicename
);
109 if (LPT
[x
].devicename
) {
112 fprintf(stderr
, "comm: LPT%d = %s\n",x
,LPT
[x
].devicename
);
113 free(LPT
[x
].devicename
);
118 struct DosDeviceStruct
*GetDeviceStruct(int fd
)
122 for (x
=0; x
!=MAX_PORTS
; x
++) {
132 int ValidCOMPort(int x
)
134 return(x
< MAX_PORTS
? (int) COM
[x
].devicename
: 0);
137 int ValidLPTPort(int x
)
139 return(x
< MAX_PORTS
? (int) LPT
[x
].devicename
: 0);
151 int BuildCommDCB(LPSTR device
, DCB FAR
*lpdcb
)
153 /* "COM1:9600,n,8,1" */
157 char *ptr
, *ptr2
, temp
[256],temp2
[10];
160 fprintf(stderr
,"BuildCommDCB: (%s), ptr %d\n", device
, lpdcb
);
164 if (!strncmp(device
,"COM",3)) {
165 port
= device
[3] - '0';
167 if (!ValidCOMPort(port
)) {
168 commerror
= IE_BADID
;
173 commerror
= IE_NOPEN
;
176 lpdcb
->Id
= COM
[port
].fd
;
181 if (*(device
+4) != ':')
184 strcpy(temp
,device
+5);
185 ptr
= strtok(temp
, ",");
187 fprintf(stderr
,"BuildCommDCB: baudrate (%s)\n", ptr
);
188 lpdcb
->BaudRate
= atoi(ptr
);
190 ptr
= strtok(NULL
, ",");
192 *ptr
= toupper(*ptr
);
194 fprintf(stderr
,"BuildCommDCB: parity (%c)\n", *ptr
);
197 lpdcb
->Parity
= NOPARITY
;
204 lpdcb
->Parity
= EVENPARITY
;
207 lpdcb
->Parity
= MARKPARITY
;
210 lpdcb
->Parity
= ODDPARITY
;
213 fprintf(stderr
,"comm: unknown parity `%c'!\n", *ptr
);
217 ptr
= strtok(NULL
, ",");
218 fprintf(stderr
, "BuildCommDCB: charsize (%c)\n", *ptr
);
219 lpdcb
->ByteSize
= *ptr
- '0';
221 ptr
= strtok(NULL
, ",");
222 fprintf(stderr
, "BuildCommDCB: stopbits (%c)\n", *ptr
);
225 lpdcb
->StopBits
= ONESTOPBIT
;
228 lpdcb
->StopBits
= TWOSTOPBITS
;
231 fprintf(stderr
,"comm: unknown # of stopbits `%c'!\n", *ptr
);
239 int OpenComm(LPSTR device
, UINT cbInQueue
, UINT cbOutQueue
)
244 fprintf(stderr
,"OpenComm: %s, %d, %d\n", device
, cbInQueue
, cbOutQueue
);
249 if (!strncmp(device
,"COM",3)) {
250 port
= device
[3] - '0';
252 if (!ValidCOMPort(port
)) {
253 commerror
= IE_BADID
;
261 fd
= open(COM
[port
].devicename
, O_RDWR
| O_NONBLOCK
, 0);
263 commerror
= WinError();
271 if (!strncmp(device
,"LPT",3)) {
272 port
= device
[3] - '0';
274 if (!ValidLPTPort(port
)) {
275 commerror
= IE_BADID
;
283 fd
= open(LPT
[port
].devicename
, O_RDWR
| O_NONBLOCK
, 0);
285 commerror
= WinError();
295 int CloseComm(int fd
)
300 fprintf(stderr
,"CloseComm: fd %d\n", fd
);
303 if (close(fd
) == -1) {
304 commerror
= WinError();
312 int SetCommBreak(int fd
)
314 struct DosDeviceStruct
*ptr
;
317 fprintf(stderr
,"SetCommBreak: fd: %d\n", fd
);
320 if ((ptr
= GetDeviceStruct(fd
)) == NULL
) {
321 commerror
= IE_BADID
;
330 int ClearCommBreak(int fd
)
332 struct DosDeviceStruct
*ptr
;
335 fprintf(stderr
,"ClearCommBreak: fd: %d\n", fd
);
338 if ((ptr
= GetDeviceStruct(fd
)) == NULL
) {
339 commerror
= IE_BADID
;
348 LONG
EscapeCommFunction(int fd
, int nFunction
)
354 fprintf(stderr
,"EscapeCommFunction fd: %d, function: %d\n", fd
, nFunction
);
357 if (tcgetattr(fd
, &port
) == -1) {
358 commerror
= WinError();
367 for (max
= 0;COM
[max
].devicename
;max
++)
373 for (max
= 0;LPT
[max
].devicename
;max
++)
379 port
.c_cflag
&= TIOCM_DTR
;
383 port
.c_cflag
&= TIOCM_RTS
;
387 port
.c_cflag
|= CRTSCTS
;
391 port
.c_cflag
|= CRTSCTS
;
395 port
.c_iflag
|= IXOFF
;
399 port
.c_iflag
|= IXON
;
403 fprintf(stderr
,"EscapeCommFunction fd: %d, unknown function: %d\n", fd
, nFunction
);
407 if (tcsetattr(fd
, TCSADRAIN
, &port
) == -1) {
408 commerror
= WinError();
416 int FlushComm(int fd
, int fnQueue
)
421 fprintf(stderr
,"FlushComm fd: %d, queue: %d\n", fd
, fnQueue
);
432 fprintf(stderr
,"FlushComm fd: %d, UNKNOWN queue: %d\n", fd
, fnQueue
);
436 if (tcflush(fd
, fnQueue
)) {
437 commerror
= WinError();
445 int GetCommError(int fd
, COMSTAT FAR
*lpStat
)
448 fprintf(stderr
,"GetCommError: fd %d (current error %d)\n", fd
, commerror
);
454 UINT FAR
* SetCommEventMask(int fd
, UINT fuEvtMask
)
457 fprintf(stderr
,"SetCommEventMask: fd %d, mask %d\n", fd
, fuEvtMask
);
460 eventmask
|= fuEvtMask
;
461 return (UINT
*)&eventmask
;
464 UINT
GetCommEventMask(int fd
, int fnEvtClear
)
467 fprintf(stderr
,"GetCommEventMask: fd %d, mask %d\n", fd
, fnEvtClear
);
469 eventmask
&= ~fnEvtClear
;
473 int SetCommState(DCB FAR
*lpdcb
)
478 fprintf(stderr
,"SetCommState: fd %d, ptr %d\n", lpdcb
->Id
, lpdcb
);
481 if (tcgetattr(lpdcb
->Id
, &port
) == -1) {
482 commerror
= WinError();
487 port
.c_cc
[VTIME
] = 0;
489 fprintf(stderr
,"SetCommState: baudrate %d\n",lpdcb
->BaudRate
);
491 port
.c_cflag
&= ~CBAUD
;
492 switch (lpdcb
->BaudRate
) {
495 port
.c_cflag
|= B110
;
499 port
.c_cflag
|= B300
;
503 port
.c_cflag
|= B600
;
507 port
.c_cflag
|= B1200
;
511 port
.c_cflag
|= B2400
;
515 port
.c_cflag
|= B4800
;
519 port
.c_cflag
|= B9600
;
523 port
.c_cflag
|= B19200
;
527 port
.c_cflag
|= B38400
;
530 commerror
= IE_BAUDRATE
;
534 switch (lpdcb
->BaudRate
) {
537 port
.c_ospeed
= B110
;
541 port
.c_ospeed
= B300
;
545 port
.c_ospeed
= B600
;
549 port
.c_ospeed
= B1200
;
553 port
.c_ospeed
= B2400
;
557 port
.c_ospeed
= B4800
;
561 port
.c_ospeed
= B9600
;
565 port
.c_ospeed
= B19200
;
569 port
.c_ospeed
= B38400
;
572 commerror
= IE_BAUDRATE
;
575 port
.c_ispeed
= port
.c_ospeed
;
577 fprintf(stderr
,"SetCommState: bytesize %d\n",lpdcb
->ByteSize
);
578 port
.c_cflag
&= ~CSIZE
;
579 switch (lpdcb
->ByteSize
) {
593 commerror
= IE_BYTESIZE
;
597 fprintf(stderr
,"SetCommState: parity %d\n",lpdcb
->Parity
);
598 port
.c_cflag
&= ~(PARENB
| PARODD
);
600 switch (lpdcb
->Parity
) {
602 port
.c_iflag
&= ~INPCK
;
605 port
.c_cflag
|= (PARENB
| PARODD
);
606 port
.c_iflag
|= INPCK
;
609 port
.c_cflag
|= PARENB
;
610 port
.c_iflag
|= INPCK
;
613 commerror
= IE_BYTESIZE
;
618 fprintf(stderr
,"SetCommState: stopbits %d\n",lpdcb
->StopBits
);
619 switch (lpdcb
->StopBits
) {
621 port
.c_cflag
&= ~CSTOPB
;
624 port
.c_cflag
|= CSTOPB
;
627 commerror
= IE_BYTESIZE
;
631 if (lpdcb
->fDtrflow
|| lpdcb
->fRtsflow
|| lpdcb
->fOutxCtsFlow
)
632 port
.c_cflag
|= CRTSCTS
;
634 if (lpdcb
->fDtrDisable
)
635 port
.c_cflag
&= ~CRTSCTS
;
638 port
.c_iflag
|= IXON
;
640 port
.c_iflag
|= IXOFF
;
642 if (tcsetattr(lpdcb
->Id
, TCSADRAIN
, &port
) == -1) {
643 commerror
= WinError();
651 int GetCommState(int fd
, DCB FAR
*lpdcb
)
656 fprintf(stderr
,"GetCommState: fd %d, ptr %d\n", fd
, lpdcb
);
659 if (tcgetattr(fd
, &port
) == -1) {
660 commerror
= WinError();
667 switch (port
.c_cflag
& CBAUD
) {
669 switch (port
.c_ospeed
) {
672 lpdcb
->BaudRate
= 110;
675 lpdcb
->BaudRate
= 300;
678 lpdcb
->BaudRate
= 600;
681 lpdcb
->BaudRate
= 1200;
684 lpdcb
->BaudRate
= 2400;
687 lpdcb
->BaudRate
= 4800;
690 lpdcb
->BaudRate
= 9600;
693 lpdcb
->BaudRate
= 19200;
696 lpdcb
->BaudRate
= 38400;
700 switch (port
.c_cflag
& CSIZE
) {
715 switch (port
.c_cflag
& ~(PARENB
| PARODD
)) {
717 lpdcb
->fParity
= NOPARITY
;
720 lpdcb
->fParity
= EVENPARITY
;
722 case (PARENB
| PARODD
):
723 lpdcb
->fParity
= ODDPARITY
;
727 if (port
.c_cflag
& CSTOPB
)
728 lpdcb
->StopBits
= TWOSTOPBITS
;
730 lpdcb
->StopBits
= ONESTOPBIT
;
732 lpdcb
->RlsTimeout
= 50;
733 lpdcb
->CtsTimeout
= 50;
734 lpdcb
->DsrTimeout
= 50;
739 lpdcb
->fDtrDisable
= 0;
740 if (port
.c_cflag
& CRTSCTS
) {
743 lpdcb
->fOutxCtsFlow
= 1;
744 lpdcb
->fOutxDsrFlow
= 1;
746 lpdcb
->fDtrDisable
= 1;
748 if (port
.c_iflag
& IXON
)
753 if (port
.c_iflag
& IXOFF
)
768 int TransmitCommChar(int fd
, char chTransmit
)
770 struct DosDeviceStruct
*ptr
;
773 fprintf(stderr
,"TransmitCommChar: fd %d, data %d \n", fd
, chTransmit
);
776 if ((ptr
= GetDeviceStruct(fd
)) == NULL
) {
777 commerror
= IE_BADID
;
781 if (ptr
->suspended
) {
782 commerror
= IE_HARDWARE
;
786 if (write(fd
, (void *) &chTransmit
, 1) == -1) {
787 commerror
= WinError();
795 int UngetCommChar(int fd
, char chUnget
)
797 struct DosDeviceStruct
*ptr
;
800 fprintf(stderr
,"UngetCommChar: fd %d (char %d)\n", fd
, chUnget
);
802 fprintf(stderr
,"NOT implemented!\n");
804 if ((ptr
= GetDeviceStruct(fd
)) == NULL
) {
805 commerror
= IE_BADID
;
809 if (ptr
->suspended
) {
810 commerror
= IE_HARDWARE
;
818 int ReadComm(int fd
, LPSTR lpvBuf
, int cbRead
)
820 struct DosDeviceStruct
*ptr
;
822 fprintf(stderr
,"ReadComm: fd %d, ptr %d, length %d\n", fd
, lpvBuf
, cbRead
);
824 if ((ptr
= GetDeviceStruct(fd
)) == NULL
) {
825 commerror
= IE_BADID
;
829 if (ptr
->suspended
) {
830 commerror
= IE_HARDWARE
;
834 if (read(fd
, (void *) lpvBuf
, cbRead
) == -1) {
835 commerror
= WinError();
843 int WriteComm(int fd
, LPSTR lpvBuf
, int cbWrite
)
846 struct DosDeviceStruct
*ptr
;
849 fprintf(stderr
,"WriteComm: fd %d, ptr %d, length %d\n", fd
, lpvBuf
, cbWrite
);
852 if ((ptr
= GetDeviceStruct(fd
)) == NULL
) {
853 commerror
= IE_BADID
;
857 if (ptr
->suspended
) {
858 commerror
= IE_HARDWARE
;
862 for (x
=0; x
!= cbWrite
; x
++)
863 fprintf(stderr
,"%c", *(lpvBuf
+ x
) );
865 if (write(fd
, (void *) lpvBuf
, cbWrite
) == -1) {
866 commerror
= WinError();